IDEMPIERE-5093 Scheduler cron pattern scheduling is always using serv… (#1270)
* IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone * minor fix for oracle/202203240830_IDEMPIERE-5093.sql * IDEMPIERE-5093 cheduler cron pattern scheduling is always using server time zone - add time zone comment for cronpattern field - use fix format for elapsed time (day'hour:minutes:seconds.millisecond) - use time zone formatting at server monitor - include etc/gmt* timezone id. fix handling of invalid user input - fix wrong editor (date) use for timestamp with time zone field * IDEMPIERE-5093 cheduler cron pattern scheduling is always using server time zone - Fix MSchedule.getNextRunMS call. * IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone - add T_Timestamp to Test table and window. - fix date time editor doesn't capture seconds for timestamp with time zone. - date time editor: use tenant time zone (if set), fallback to browser time zone. - date time editor: fix processing of timestamp with time zone value. - time zone editor: drop the confusing etc/gmt* entries and support entry of GMT(+/-)hh:mm custom zone id. * IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone Fix NPE Co-authored-by: Carlos Ruiz <carg67@gmail.com>
This commit is contained in:
parent
1928bba1b6
commit
13b37c4acc
|
@ -0,0 +1,51 @@
|
||||||
|
SELECT register_migration_script('202203240830_IDEMPIERE-5093.sql') FROM dual
|
||||||
|
;
|
||||||
|
|
||||||
|
SET SQLBLANKLINES ON
|
||||||
|
SET DEFINE OFF
|
||||||
|
|
||||||
|
-- IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone
|
||||||
|
-- Mar 24, 2022 3:21:34 PM MYT
|
||||||
|
INSERT INTO AD_Reference (AD_Reference_ID,Name,AD_Reference_UU,IsOrderByValue,AD_Org_ID,Description,ValidationType,Updated,IsActive,CreatedBy,UpdatedBy,AD_Client_ID,Created,EntityType) VALUES (200133,'Timestamp With Time Zone','a4c9a3f1-ecbb-4beb-ac16-d1b66279f698','N',0,'Date and time with time zone','D',TO_DATE('2022-03-24 15:27:01','YYYY-MM-DD HH24:MI:SS'),'Y',100,100,0,TO_DATE('2022-03-24 15:27:01','YYYY-MM-DD HH24:MI:SS'),'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:21:34 PM MYT
|
||||||
|
INSERT INTO AD_Reference (AD_Reference_ID,Name,AD_Reference_UU,IsOrderByValue,AD_Org_ID,Description,ValidationType,Updated,IsActive,CreatedBy,UpdatedBy,AD_Client_ID,Created,EntityType) VALUES (200135,'Time Zone','9420d498-a217-4c35-a638-b6fcf462538e','N',0,'Time Zone','D',TO_DATE('2022-03-24 15:21:27','YYYY-MM-DD HH24:MI:SS'),'Y',100,100,0,TO_DATE('2022-03-24 15:21:27','YYYY-MM-DD HH24:MI:SS'),'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:34 PM MYT
|
||||||
|
UPDATE AD_Column SET AD_Reference_ID=200133,Updated=TO_DATE('2022-03-24 15:27:34','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Column_ID=11264
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:42 PM MYT
|
||||||
|
ALTER TABLE AD_Scheduler MODIFY DateLastRun TIMESTAMP WITH TIME ZONE DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:59 PM MYT
|
||||||
|
UPDATE AD_Column SET AD_Reference_ID=200133,Updated=TO_DATE('2022-03-24 15:27:59','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Column_ID=11257
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:28:04 PM MYT
|
||||||
|
ALTER TABLE AD_Scheduler MODIFY DateNextRun TIMESTAMP WITH TIME ZONE DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:39:53 PM MYT
|
||||||
|
INSERT INTO AD_Element (AD_Element_ID,ColumnName,Updated,Name,Description,PrintName,AD_Element_UU,IsActive,Created,AD_Org_ID,CreatedBy,UpdatedBy,AD_Client_ID,EntityType) VALUES (203049,'TimeZone',TO_DATE('2022-03-24 15:39:47','YYYY-MM-DD HH24:MI:SS'),'Time Zone','Time zone name','Time Zone','90009634-4025-4850-a73e-0cdb0b06994b','Y',TO_DATE('2022-03-24 15:39:47','YYYY-MM-DD HH24:MI:SS'),0,100,100,0,'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:41:07 PM MYT
|
||||||
|
INSERT INTO AD_Column (AD_Column_ID,SeqNoSelection,IsSyncDatabase,Version,IsMandatory,IsTranslated,IsIdentifier,SeqNo,IsParent,FieldLength,IsSelectionColumn,IsKey,IsAutocomplete,IsAllowLogging,AD_Column_UU,Updated,IsUpdateable,ColumnName,Description,Name,IsAllowCopy,IsActive,CreatedBy,UpdatedBy,IsToolbarButton,IsAlwaysUpdateable,AD_Client_ID,AD_Org_ID,Created,EntityType,IsEncrypted,IsSecure,FKConstraintType,AD_Element_ID,AD_Reference_ID,AD_Table_ID) VALUES (212855,0,'N',1,'N','N','N',0,'N',60,'N','N','N','Y','17152afe-47ff-4610-8765-aec3a5d56b19',TO_DATE('2022-03-24 15:41:02','YYYY-MM-DD HH24:MI:SS'),'Y','TimeZone','Time zone name','Time Zone','Y','Y',100,100,'N','N',0,0,TO_DATE('2022-03-24 15:41:02','YYYY-MM-DD HH24:MI:SS'),'D','N','N','N',203049,200135,227)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:41:15 PM MYT
|
||||||
|
ALTER TABLE AD_ClientInfo ADD TimeZone VARCHAR2(60 CHAR) DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:42:03 PM MYT
|
||||||
|
INSERT INTO AD_Field (SortNo,AD_Field_ID,IsEncrypted,DisplayLength,IsSameLine,IsHeading,SeqNo,IsCentrallyMaintained,IsReadOnly,AD_Org_ID,Updated,Description,Name,AD_Field_UU,IsDisplayed,IsFieldOnly,CreatedBy,UpdatedBy,IsActive,IsDisplayedGrid,SeqNoGrid,XPosition,IsQuickEntry,AD_Client_ID,Created,ColumnSpan,NumLines,IsAdvancedField,IsDefaultFocus,AD_Column_ID,AD_FieldGroup_ID,EntityType,AD_Tab_ID) VALUES (0,204287,'N',0,'N','N',1020,'Y','N',0,TO_DATE('2022-03-24 15:42:03','YYYY-MM-DD HH24:MI:SS'),'Time zone name','Time Zone','16686d03-b85e-4b58-a0a4-21e99fa4303c','Y','N',100,100,'Y','Y',1020,1,'N',0,TO_DATE('2022-03-24 15:42:03','YYYY-MM-DD HH24:MI:SS'),2,1,'N','N',212855,118,'D',169)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 4:43:42 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=45,SeqNoGrid=45,Updated=TO_DATE('2022-03-24 16:43:43','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Field_ID=204287
|
||||||
|
;
|
||||||
|
|
|
@ -0,0 +1,36 @@
|
||||||
|
-- IDEMPIERE-5093 cheduler cron pattern scheduling is always using server time zone
|
||||||
|
SELECT register_migration_script('202204041140_IDEMPIERE-5093.sql') FROM dual;
|
||||||
|
|
||||||
|
SET SQLBLANKLINES ON
|
||||||
|
SET DEFINE OFF
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Element SET Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.',Updated=TO_TIMESTAMP('2022-04-04 11:40:38','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Element_ID=54124
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Column SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Process_Para SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', AD_Element_ID=54124 WHERE UPPER(ColumnName)='CRONPATTERN' AND IsCentrallyMaintained='Y' AND AD_Element_ID IS NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Process_Para SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124 AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_InfoColumn SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124 AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Field SET Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Column_ID IN (SELECT AD_Column_ID FROM AD_Column WHERE AD_Element_ID=54124) AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
|
@ -0,0 +1,186 @@
|
||||||
|
-- IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone
|
||||||
|
SELECT register_migration_script('202204111508_IDEMPIERE-5093.sql') FROM dual;
|
||||||
|
|
||||||
|
SET SQLBLANKLINES ON
|
||||||
|
SET DEFINE OFF
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:09:15 PM MYT
|
||||||
|
INSERT INTO AD_Element (AD_Element_ID,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,ColumnName,Name,Description,PrintName,EntityType,AD_Element_UU) VALUES (203573,0,0,'Y',TO_TIMESTAMP('2022-04-11 15:09:13','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:09:13','YYYY-MM-DD HH24:MI:SS'),100,'T_Timestamp','Timestamp','Timestamp with time zone','Timestamp','D','0e993a88-2c26-4946-9ca8-2eb4263d4323')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:16:46 PM MYT
|
||||||
|
INSERT INTO AD_Column (AD_Column_ID,Version,Name,Description,AD_Table_ID,ColumnName,FieldLength,IsKey,IsParent,IsMandatory,IsTranslated,IsIdentifier,SeqNo,IsEncrypted,AD_Reference_ID,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,AD_Element_ID,IsUpdateable,IsSelectionColumn,EntityType,IsSyncDatabase,IsAlwaysUpdateable,IsAutocomplete,IsAllowLogging,AD_Column_UU,IsAllowCopy,SeqNoSelection,IsToolbarButton,IsSecure,FKConstraintType,IsHtml) VALUES (214755,0,'Timestamp','Timestamp with time zone',135,'T_Timestamp',10,'N','N','N','N','N',0,'N',200133,0,0,'Y',TO_TIMESTAMP('2022-04-11 15:16:45','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:16:45','YYYY-MM-DD HH24:MI:SS'),100,203573,'Y','N','D','N','N','N','Y','ec1dd52b-d346-4ca3-ac50-6f87008ee99a','Y',0,'N','N','N','N')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:16:52 PM MYT
|
||||||
|
ALTER TABLE Test ADD T_Timestamp TIMESTAMP WITH TIME ZONE DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:17:54 PM MYT
|
||||||
|
INSERT INTO AD_Field (AD_Field_ID,Name,Description,AD_Tab_ID,AD_Column_ID,IsDisplayed,DisplayLength,SeqNo,SortNo,IsSameLine,IsHeading,IsFieldOnly,IsEncrypted,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,IsReadOnly,IsCentrallyMaintained,EntityType,AD_Field_UU,IsDisplayedGrid,SeqNoGrid,XPosition,ColumnSpan,NumLines,IsQuickEntry,IsDefaultFocus,IsAdvancedField,IsQuickForm) VALUES (206945,'Timestamp','Timestamp with time zone',152,214755,'Y',0,270,0,'N','N','N','N',0,0,'Y',TO_TIMESTAMP('2022-04-11 15:17:54','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:17:54','YYYY-MM-DD HH24:MI:SS'),100,'N','Y','D','e95039ef-5430-473b-8f92-3caf99d6d914','Y',280,1,2,1,'N','N','N','N')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=150,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=206945
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=160,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3209
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=170,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3902
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=180,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3210
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=190,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=4251
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=200,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3057
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=210,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3056
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=220,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=205590
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=230,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=8351
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=240,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=8352
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=250,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3060
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=260,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3061
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=270,IsDisplayed='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=206818
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=2024
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=415
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=416
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=10,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=417
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=20,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=418
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=30,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=419
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=40,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=420
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=50,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=421
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=60,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=422
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=70,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=423
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=80,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=424
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=90,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3059
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=100,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3062
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=110,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=425
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=120,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=426
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=130,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=206945
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=140,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3057
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=150,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3056
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=160,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3902
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=170,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=4251
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=180,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3209
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=190,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3210
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=200,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=8351
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=210,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=8352
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=220,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3060
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=230,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=3061
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=240,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=205590
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=250,IsDisplayedGrid='Y', Updated=getDate(), UpdatedBy=100 WHERE AD_Field_ID=206818
|
||||||
|
;
|
||||||
|
|
|
@ -0,0 +1,48 @@
|
||||||
|
SELECT register_migration_script('202203240830_IDEMPIERE-5093.sql') FROM dual
|
||||||
|
;
|
||||||
|
|
||||||
|
-- IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone
|
||||||
|
-- Mar 24, 2022 3:21:34 PM MYT
|
||||||
|
INSERT INTO AD_Reference (AD_Reference_ID,Name,AD_Reference_UU,IsOrderByValue,AD_Org_ID,Description,ValidationType,Updated,IsActive,CreatedBy,UpdatedBy,AD_Client_ID,Created,EntityType) VALUES (200133,'Timestamp With Time Zone','a4c9a3f1-ecbb-4beb-ac16-d1b66279f698','N',0,'Date and time with time zone','D',TO_TIMESTAMP('2022-03-24 15:27:01','YYYY-MM-DD HH24:MI:SS'),'Y',100,100,0,TO_TIMESTAMP('2022-03-24 15:27:01','YYYY-MM-DD HH24:MI:SS'),'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:21:34 PM MYT
|
||||||
|
INSERT INTO AD_Reference (AD_Reference_ID,Name,AD_Reference_UU,IsOrderByValue,AD_Org_ID,Description,ValidationType,Updated,IsActive,CreatedBy,UpdatedBy,AD_Client_ID,Created,EntityType) VALUES (200135,'Time Zone','9420d498-a217-4c35-a638-b6fcf462538e','N',0,'Time Zone','D',TO_TIMESTAMP('2022-03-24 15:21:27','YYYY-MM-DD HH24:MI:SS'),'Y',100,100,0,TO_TIMESTAMP('2022-03-24 15:21:27','YYYY-MM-DD HH24:MI:SS'),'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:34 PM MYT
|
||||||
|
UPDATE AD_Column SET AD_Reference_ID=200133,Updated=TO_TIMESTAMP('2022-03-24 15:27:34','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Column_ID=11264
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:42 PM MYT
|
||||||
|
INSERT INTO t_alter_column values('ad_scheduler','DateLastRun','TIMESTAMP WITH TIME ZONE','NULL',null)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:27:59 PM MYT
|
||||||
|
UPDATE AD_Column SET AD_Reference_ID=200133,Updated=TO_TIMESTAMP('2022-03-24 15:27:59','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Column_ID=11257
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:28:04 PM MYT
|
||||||
|
INSERT INTO t_alter_column values('ad_scheduler','DateNextRun','TIMESTAMP WITH TIME ZONE','NULL',null)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:39:53 PM MYT
|
||||||
|
INSERT INTO AD_Element (AD_Element_ID,ColumnName,Updated,Name,Description,PrintName,AD_Element_UU,IsActive,Created,AD_Org_ID,CreatedBy,UpdatedBy,AD_Client_ID,EntityType) VALUES (203049,'TimeZone',TO_TIMESTAMP('2022-03-24 15:39:47','YYYY-MM-DD HH24:MI:SS'),'Time Zone','Time zone name','Time Zone','90009634-4025-4850-a73e-0cdb0b06994b','Y',TO_TIMESTAMP('2022-03-24 15:39:47','YYYY-MM-DD HH24:MI:SS'),0,100,100,0,'D')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:41:07 PM MYT
|
||||||
|
INSERT INTO AD_Column (AD_Column_ID,SeqNoSelection,IsSyncDatabase,Version,IsMandatory,IsTranslated,IsIdentifier,SeqNo,IsParent,FieldLength,IsSelectionColumn,IsKey,IsAutocomplete,IsAllowLogging,AD_Column_UU,Updated,IsUpdateable,ColumnName,Description,Name,IsAllowCopy,IsActive,CreatedBy,UpdatedBy,IsToolbarButton,IsAlwaysUpdateable,AD_Client_ID,AD_Org_ID,Created,EntityType,IsEncrypted,IsSecure,FKConstraintType,AD_Element_ID,AD_Reference_ID,AD_Table_ID) VALUES (212855,0,'N',1,'N','N','N',0,'N',60,'N','N','N','Y','17152afe-47ff-4610-8765-aec3a5d56b19',TO_TIMESTAMP('2022-03-24 15:41:02','YYYY-MM-DD HH24:MI:SS'),'Y','TimeZone','Time zone name','Time Zone','Y','Y',100,100,'N','N',0,0,TO_TIMESTAMP('2022-03-24 15:41:02','YYYY-MM-DD HH24:MI:SS'),'D','N','N','N',203049,200135,227)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:41:15 PM MYT
|
||||||
|
ALTER TABLE AD_ClientInfo ADD COLUMN TimeZone VARCHAR(60) DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 3:42:03 PM MYT
|
||||||
|
INSERT INTO AD_Field (SortNo,AD_Field_ID,IsEncrypted,DisplayLength,IsSameLine,IsHeading,SeqNo,IsCentrallyMaintained,IsReadOnly,AD_Org_ID,Updated,Description,Name,AD_Field_UU,IsDisplayed,IsFieldOnly,CreatedBy,UpdatedBy,IsActive,IsDisplayedGrid,SeqNoGrid,XPosition,IsQuickEntry,AD_Client_ID,Created,ColumnSpan,NumLines,IsAdvancedField,IsDefaultFocus,AD_Column_ID,AD_FieldGroup_ID,EntityType,AD_Tab_ID) VALUES (0,204287,'N',0,'N','N',1020,'Y','N',0,TO_TIMESTAMP('2022-03-24 15:42:03','YYYY-MM-DD HH24:MI:SS'),'Time zone name','Time Zone','16686d03-b85e-4b58-a0a4-21e99fa4303c','Y','N',100,100,'Y','Y',1020,1,'N',0,TO_TIMESTAMP('2022-03-24 15:42:03','YYYY-MM-DD HH24:MI:SS'),2,1,'N','N',212855,118,'D',169)
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Mar 24, 2022 4:43:43 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=45,SeqNoGrid=45,Updated=TO_TIMESTAMP('2022-03-24 16:43:43','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Field_ID=204287
|
||||||
|
;
|
||||||
|
|
|
@ -0,0 +1,33 @@
|
||||||
|
-- IDEMPIERE-5093 cheduler cron pattern scheduling is always using server time zone
|
||||||
|
SELECT register_migration_script('202204041140_IDEMPIERE-5093.sql') FROM dual;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Element SET Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.',Updated=TO_TIMESTAMP('2022-04-04 11:40:38','YYYY-MM-DD HH24:MI:SS'),UpdatedBy=100 WHERE AD_Element_ID=54124
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Column SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Process_Para SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', AD_Element_ID=54124 WHERE UPPER(ColumnName)='CRONPATTERN' AND IsCentrallyMaintained='Y' AND AD_Element_ID IS NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Process_Para SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124 AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_InfoColumn SET ColumnName='CronPattern', Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Element_ID=54124 AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 4, 2022, 11:40:38 AM MYT
|
||||||
|
UPDATE AD_Field SET Name='Cron Scheduling Pattern', Description='Cron pattern to define when the process should be invoked.', Help='Cron pattern to define when the process should be invoked. See http://www.sauronsoftware.it/projects/cron4j/api/it/sauronsoftware/cron4j/SchedulingPattern.html
|
||||||
|
If set, the time zone from tenant info is used. Otherwise, use the default JVM time zone at the server.', Placeholder=NULL WHERE AD_Column_ID IN (SELECT AD_Column_ID FROM AD_Column WHERE AD_Element_ID=54124) AND IsCentrallyMaintained='Y'
|
||||||
|
;
|
||||||
|
|
|
@ -0,0 +1,183 @@
|
||||||
|
-- IDEMPIERE-5093 Scheduler cron pattern scheduling is always using server time zone
|
||||||
|
SELECT register_migration_script('202204111508_IDEMPIERE-5093.sql') FROM dual;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:09:15 PM MYT
|
||||||
|
INSERT INTO AD_Element (AD_Element_ID,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,ColumnName,Name,Description,PrintName,EntityType,AD_Element_UU) VALUES (203573,0,0,'Y',TO_TIMESTAMP('2022-04-11 15:09:13','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:09:13','YYYY-MM-DD HH24:MI:SS'),100,'T_Timestamp','Timestamp','Timestamp with time zone','Timestamp','D','0e993a88-2c26-4946-9ca8-2eb4263d4323')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:16:46 PM MYT
|
||||||
|
INSERT INTO AD_Column (AD_Column_ID,Version,Name,Description,AD_Table_ID,ColumnName,FieldLength,IsKey,IsParent,IsMandatory,IsTranslated,IsIdentifier,SeqNo,IsEncrypted,AD_Reference_ID,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,AD_Element_ID,IsUpdateable,IsSelectionColumn,EntityType,IsSyncDatabase,IsAlwaysUpdateable,IsAutocomplete,IsAllowLogging,AD_Column_UU,IsAllowCopy,SeqNoSelection,IsToolbarButton,IsSecure,FKConstraintType,IsHtml) VALUES (214755,0,'Timestamp','Timestamp with time zone',135,'T_Timestamp',10,'N','N','N','N','N',0,'N',200133,0,0,'Y',TO_TIMESTAMP('2022-04-11 15:16:45','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:16:45','YYYY-MM-DD HH24:MI:SS'),100,203573,'Y','N','D','N','N','N','Y','ec1dd52b-d346-4ca3-ac50-6f87008ee99a','Y',0,'N','N','N','N')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:16:52 PM MYT
|
||||||
|
ALTER TABLE Test ADD COLUMN T_Timestamp TIMESTAMP WITH TIME ZONE DEFAULT NULL
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:17:54 PM MYT
|
||||||
|
INSERT INTO AD_Field (AD_Field_ID,Name,Description,AD_Tab_ID,AD_Column_ID,IsDisplayed,DisplayLength,SeqNo,SortNo,IsSameLine,IsHeading,IsFieldOnly,IsEncrypted,AD_Client_ID,AD_Org_ID,IsActive,Created,CreatedBy,Updated,UpdatedBy,IsReadOnly,IsCentrallyMaintained,EntityType,AD_Field_UU,IsDisplayedGrid,SeqNoGrid,XPosition,ColumnSpan,NumLines,IsQuickEntry,IsDefaultFocus,IsAdvancedField,IsQuickForm) VALUES (206945,'Timestamp','Timestamp with time zone',152,214755,'Y',0,270,0,'N','N','N','N',0,0,'Y',TO_TIMESTAMP('2022-04-11 15:17:54','YYYY-MM-DD HH24:MI:SS'),100,TO_TIMESTAMP('2022-04-11 15:17:54','YYYY-MM-DD HH24:MI:SS'),100,'N','Y','D','e95039ef-5430-473b-8f92-3caf99d6d914','Y',280,1,2,1,'N','N','N','N')
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=150,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=206945
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=160,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3209
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=170,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3902
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=180,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3210
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=190,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=4251
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=200,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3057
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=210,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3056
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=220,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=205590
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=230,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=8351
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=240,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=8352
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=250,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3060
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=260,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3061
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:15 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNo=270,IsDisplayed='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=206818
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=2024
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=415
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=0,IsDisplayedGrid='N', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=416
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=10,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=417
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=20,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=418
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=30,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=419
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=40,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=420
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=50,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=421
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=60,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=422
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=70,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=423
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=80,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=424
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=90,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3059
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=100,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3062
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=110,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=425
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=120,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=426
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=130,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=206945
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=140,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3057
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=150,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3056
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=160,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3902
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=170,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=4251
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=180,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3209
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=190,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3210
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=200,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=8351
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=210,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=8352
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=220,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3060
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=230,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=3061
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=240,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=205590
|
||||||
|
;
|
||||||
|
|
||||||
|
-- Apr 11, 2022, 3:18:28 PM MYT
|
||||||
|
UPDATE AD_Field SET SeqNoGrid=250,IsDisplayedGrid='Y', Updated=statement_timestamp(), UpdatedBy=100 WHERE AD_Field_ID=206818
|
||||||
|
;
|
||||||
|
|
|
@ -407,6 +407,11 @@ public interface AdempiereDatabase
|
||||||
*/
|
*/
|
||||||
public String getTimestampDataType();
|
public String getTimestampDataType();
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @return timestamp with time zone type name
|
||||||
|
*/
|
||||||
|
public String getTimestampWithTimezoneDataType();
|
||||||
/**
|
/**
|
||||||
* Get SQL Create
|
* Get SQL Create
|
||||||
* @param table
|
* @param table
|
||||||
|
|
|
@ -22,7 +22,7 @@ import org.compiere.util.KeyNamePair;
|
||||||
|
|
||||||
/** Generated Interface for AD_ClientInfo
|
/** Generated Interface for AD_ClientInfo
|
||||||
* @author iDempiere (generated)
|
* @author iDempiere (generated)
|
||||||
* @version Release 9
|
* @version Release 10
|
||||||
*/
|
*/
|
||||||
public interface I_AD_ClientInfo
|
public interface I_AD_ClientInfo
|
||||||
{
|
{
|
||||||
|
@ -44,8 +44,8 @@ public interface I_AD_ClientInfo
|
||||||
/** Column name AD_Client_ID */
|
/** Column name AD_Client_ID */
|
||||||
public static final String COLUMNNAME_AD_Client_ID = "AD_Client_ID";
|
public static final String COLUMNNAME_AD_Client_ID = "AD_Client_ID";
|
||||||
|
|
||||||
/** Get Client.
|
/** Get Tenant.
|
||||||
* Client/Tenant for this installation.
|
* Tenant for this installation.
|
||||||
*/
|
*/
|
||||||
public int getAD_Client_ID();
|
public int getAD_Client_ID();
|
||||||
|
|
||||||
|
@ -62,12 +62,12 @@ public interface I_AD_ClientInfo
|
||||||
public static final String COLUMNNAME_AD_Org_ID = "AD_Org_ID";
|
public static final String COLUMNNAME_AD_Org_ID = "AD_Org_ID";
|
||||||
|
|
||||||
/** Set Organization.
|
/** Set Organization.
|
||||||
* Organizational entity within client
|
* Organizational entity within tenant
|
||||||
*/
|
*/
|
||||||
public void setAD_Org_ID (int AD_Org_ID);
|
public void setAD_Org_ID (int AD_Org_ID);
|
||||||
|
|
||||||
/** Get Organization.
|
/** Get Organization.
|
||||||
* Organizational entity within client
|
* Organizational entity within tenant
|
||||||
*/
|
*/
|
||||||
public int getAD_Org_ID();
|
public int getAD_Org_ID();
|
||||||
|
|
||||||
|
@ -464,6 +464,19 @@ public interface I_AD_ClientInfo
|
||||||
|
|
||||||
public org.compiere.model.I_AD_StorageProvider getStorageImage() throws RuntimeException;
|
public org.compiere.model.I_AD_StorageProvider getStorageImage() throws RuntimeException;
|
||||||
|
|
||||||
|
/** Column name TimeZone */
|
||||||
|
public static final String COLUMNNAME_TimeZone = "TimeZone";
|
||||||
|
|
||||||
|
/** Set Time Zone.
|
||||||
|
* Time zone name
|
||||||
|
*/
|
||||||
|
public void setTimeZone (String TimeZone);
|
||||||
|
|
||||||
|
/** Get Time Zone.
|
||||||
|
* Time zone name
|
||||||
|
*/
|
||||||
|
public String getTimeZone();
|
||||||
|
|
||||||
/** Column name Updated */
|
/** Column name Updated */
|
||||||
public static final String COLUMNNAME_Updated = "Updated";
|
public static final String COLUMNNAME_Updated = "Updated";
|
||||||
|
|
||||||
|
|
|
@ -105,7 +105,8 @@ public class MAcctProcessor extends X_C_AcctProcessor
|
||||||
protected boolean beforeSave(boolean newRecord)
|
protected boolean beforeSave(boolean newRecord)
|
||||||
{
|
{
|
||||||
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
||||||
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern());
|
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern(),
|
||||||
|
MClientInfo.get(getCtx(), getAD_Client_ID()).getTimeZone());
|
||||||
if (nextWork > 0)
|
if (nextWork > 0)
|
||||||
setDateNextRun(new Timestamp(nextWork));
|
setDateNextRun(new Timestamp(nextWork));
|
||||||
}
|
}
|
||||||
|
|
|
@ -168,7 +168,8 @@ public class MAlertProcessor extends X_AD_AlertProcessor
|
||||||
protected boolean beforeSave(boolean newRecord)
|
protected boolean beforeSave(boolean newRecord)
|
||||||
{
|
{
|
||||||
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
||||||
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern());
|
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern(),
|
||||||
|
MClientInfo.get(getCtx(), getAD_Client_ID()).getTimeZone());
|
||||||
if (nextWork > 0)
|
if (nextWork > 0)
|
||||||
setDateNextRun(new Timestamp(nextWork));
|
setDateNextRun(new Timestamp(nextWork));
|
||||||
}
|
}
|
||||||
|
|
|
@ -242,7 +242,8 @@ public class MRequestProcessor extends X_R_RequestProcessor
|
||||||
protected boolean beforeSave(boolean newRecord)
|
protected boolean beforeSave(boolean newRecord)
|
||||||
{
|
{
|
||||||
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
||||||
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern());
|
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern(),
|
||||||
|
MClientInfo.get(getCtx(), getAD_Client_ID()).getTimeZone());
|
||||||
if (nextWork > 0)
|
if (nextWork > 0)
|
||||||
setDateNextRun(new Timestamp(nextWork));
|
setDateNextRun(new Timestamp(nextWork));
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,12 +26,14 @@ import java.sql.ResultSet;
|
||||||
import java.util.Enumeration;
|
import java.util.Enumeration;
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
import java.util.StringTokenizer;
|
import java.util.StringTokenizer;
|
||||||
|
import java.util.TimeZone;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
import java.util.regex.Matcher;
|
import java.util.regex.Matcher;
|
||||||
import java.util.regex.Pattern;
|
import java.util.regex.Pattern;
|
||||||
import java.util.regex.PatternSyntaxException;
|
import java.util.regex.PatternSyntaxException;
|
||||||
|
|
||||||
import org.compiere.util.Env;
|
import org.compiere.util.Env;
|
||||||
|
import org.compiere.util.Util;
|
||||||
import org.idempiere.cache.ImmutableIntPOCache;
|
import org.idempiere.cache.ImmutableIntPOCache;
|
||||||
import org.idempiere.cache.ImmutablePOSupport;
|
import org.idempiere.cache.ImmutablePOSupport;
|
||||||
|
|
||||||
|
@ -249,9 +251,29 @@ public class MSchedule extends X_AD_Schedule implements ImmutablePOSupport
|
||||||
/**
|
/**
|
||||||
* Get Next Run
|
* Get Next Run
|
||||||
* @param last in MS
|
* @param last in MS
|
||||||
|
* @param scheduleType
|
||||||
|
* @param frequencyType
|
||||||
|
* @param frequency
|
||||||
|
* @param cronPattern
|
||||||
* @return next run in MS
|
* @return next run in MS
|
||||||
|
* @deprecated
|
||||||
*/
|
*/
|
||||||
public static long getNextRunMS (long last, String scheduleType, String frequencyType, int frequency, String cronPattern)
|
public static long getNextRunMS (long last, String scheduleType, String frequencyType, int frequency, String cronPattern)
|
||||||
|
{
|
||||||
|
return getNextRunMS(last, scheduleType, frequencyType, frequency, cronPattern, null);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Get Next Run
|
||||||
|
* @param last in MS
|
||||||
|
* @param scheduleType
|
||||||
|
* @param frequencyType
|
||||||
|
* @param frequency
|
||||||
|
* @param cronPattern
|
||||||
|
* @param timeZone
|
||||||
|
* @return next run in MS
|
||||||
|
*/
|
||||||
|
public static long getNextRunMS (long last, String scheduleType, String frequencyType, int frequency, String cronPattern, String timeZone)
|
||||||
{
|
{
|
||||||
long now = System.currentTimeMillis();
|
long now = System.currentTimeMillis();
|
||||||
if (MSchedule.SCHEDULETYPE_Frequency.equals(scheduleType))
|
if (MSchedule.SCHEDULETYPE_Frequency.equals(scheduleType))
|
||||||
|
@ -281,11 +303,22 @@ public class MSchedule extends X_AD_Schedule implements ImmutablePOSupport
|
||||||
{
|
{
|
||||||
if (cronPattern != null && cronPattern.trim().length() > 0
|
if (cronPattern != null && cronPattern.trim().length() > 0
|
||||||
&& SchedulingPattern.validate(cronPattern)) {
|
&& SchedulingPattern.validate(cronPattern)) {
|
||||||
|
TimeZone tz = null;
|
||||||
|
if (!Util.isEmpty(timeZone)) {
|
||||||
|
tz = TimeZone.getTimeZone(timeZone);
|
||||||
|
if (tz != null && !tz.getID().equals(timeZone)) {
|
||||||
|
tz = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
Predictor predictor = new Predictor(cronPattern, last);
|
Predictor predictor = new Predictor(cronPattern, last);
|
||||||
|
if (tz != null)
|
||||||
|
predictor.setTimeZone(tz);
|
||||||
long next = predictor.nextMatchingTime();
|
long next = predictor.nextMatchingTime();
|
||||||
while (next < now)
|
while (next < now)
|
||||||
{
|
{
|
||||||
predictor = new Predictor(cronPattern, next);
|
predictor = new Predictor(cronPattern, next);
|
||||||
|
if (tz != null)
|
||||||
|
predictor.setTimeZone(tz);
|
||||||
next = predictor.nextMatchingTime();
|
next = predictor.nextMatchingTime();
|
||||||
}
|
}
|
||||||
return next;
|
return next;
|
||||||
|
|
|
@ -325,7 +325,9 @@ public class MScheduler extends X_AD_Scheduler
|
||||||
}
|
}
|
||||||
|
|
||||||
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
||||||
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern());
|
MClientInfo clientInfo = MClientInfo.get(getCtx(), getAD_Client_ID());
|
||||||
|
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern(),
|
||||||
|
clientInfo.getTimeZone());
|
||||||
if (nextWork > 0)
|
if (nextWork > 0)
|
||||||
setDateNextRun(new Timestamp(nextWork));
|
setDateNextRun(new Timestamp(nextWork));
|
||||||
}
|
}
|
||||||
|
|
|
@ -144,6 +144,8 @@ public class SystemIDs
|
||||||
public final static int REFERENCE_DATATYPE_TEXT = 14;
|
public final static int REFERENCE_DATATYPE_TEXT = 14;
|
||||||
public final static int REFERENCE_DATATYPE_TEXTLONG = 36;
|
public final static int REFERENCE_DATATYPE_TEXTLONG = 36;
|
||||||
public final static int REFERENCE_DATATYPE_TIME = 24;
|
public final static int REFERENCE_DATATYPE_TIME = 24;
|
||||||
|
public final static int REFERENCE_DATATYPE_TIMESTAMP_WITH_TIMEZONE = 200133;
|
||||||
|
public final static int REFERENCE_DATATYPE_TIMEZONE = 200135;
|
||||||
public final static int REFERENCE_DATATYPE_URL = 40;
|
public final static int REFERENCE_DATATYPE_URL = 40;
|
||||||
public final static int REFERENCE_DATATYPE_YES_NO = 20;
|
public final static int REFERENCE_DATATYPE_YES_NO = 20;
|
||||||
|
|
||||||
|
|
|
@ -23,7 +23,7 @@ import java.util.Properties;
|
||||||
|
|
||||||
/** Generated Model for AD_ClientInfo
|
/** Generated Model for AD_ClientInfo
|
||||||
* @author iDempiere (generated)
|
* @author iDempiere (generated)
|
||||||
* @version Release 9 - $Id$ */
|
* @version Release 10 - $Id$ */
|
||||||
@org.adempiere.base.Model(table="AD_ClientInfo")
|
@org.adempiere.base.Model(table="AD_ClientInfo")
|
||||||
public class X_AD_ClientInfo extends PO implements I_AD_ClientInfo, I_Persistent
|
public class X_AD_ClientInfo extends PO implements I_AD_ClientInfo, I_Persistent
|
||||||
{
|
{
|
||||||
|
@ -31,7 +31,7 @@ public class X_AD_ClientInfo extends PO implements I_AD_ClientInfo, I_Persistent
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
private static final long serialVersionUID = 20220116L;
|
private static final long serialVersionUID = 20220325L;
|
||||||
|
|
||||||
/** Standard Constructor */
|
/** Standard Constructor */
|
||||||
public X_AD_ClientInfo (Properties ctx, int AD_ClientInfo_ID, String trxName)
|
public X_AD_ClientInfo (Properties ctx, int AD_ClientInfo_ID, String trxName)
|
||||||
|
@ -823,4 +823,20 @@ public class X_AD_ClientInfo extends PO implements I_AD_ClientInfo, I_Persistent
|
||||||
return 0;
|
return 0;
|
||||||
return ii.intValue();
|
return ii.intValue();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/** Set Time Zone.
|
||||||
|
@param TimeZone Time zone name
|
||||||
|
*/
|
||||||
|
public void setTimeZone (String TimeZone)
|
||||||
|
{
|
||||||
|
set_Value (COLUMNNAME_TimeZone, TimeZone);
|
||||||
|
}
|
||||||
|
|
||||||
|
/** Get Time Zone.
|
||||||
|
@return Time zone name
|
||||||
|
*/
|
||||||
|
public String getTimeZone()
|
||||||
|
{
|
||||||
|
return (String)get_Value(COLUMNNAME_TimeZone);
|
||||||
|
}
|
||||||
}
|
}
|
|
@ -55,6 +55,8 @@ import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TABLEDIR;
|
||||||
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TEXT;
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TEXT;
|
||||||
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TEXTLONG;
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TEXTLONG;
|
||||||
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TIME;
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TIME;
|
||||||
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TIMESTAMP_WITH_TIMEZONE;
|
||||||
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_TIMEZONE;
|
||||||
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_URL;
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_URL;
|
||||||
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_YES_NO;
|
import static org.compiere.model.SystemIDs.REFERENCE_DATATYPE_YES_NO;
|
||||||
|
|
||||||
|
@ -66,6 +68,7 @@ import java.util.Currency;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Locale;
|
import java.util.Locale;
|
||||||
import java.util.Optional;
|
import java.util.Optional;
|
||||||
|
import java.util.TimeZone;
|
||||||
import java.util.logging.Level;
|
import java.util.logging.Level;
|
||||||
|
|
||||||
import org.adempiere.base.IDisplayTypeFactory;
|
import org.adempiere.base.IDisplayTypeFactory;
|
||||||
|
@ -172,6 +175,10 @@ public final class DisplayType
|
||||||
|
|
||||||
public static final int ChosenMultipleSelectionSearch = REFERENCE_DATATYPE_CHOSEN_MULTIPLE_SELECTION_SEARCH;
|
public static final int ChosenMultipleSelectionSearch = REFERENCE_DATATYPE_CHOSEN_MULTIPLE_SELECTION_SEARCH;
|
||||||
|
|
||||||
|
public static final int TimestampWithTimeZone = REFERENCE_DATATYPE_TIMESTAMP_WITH_TIMEZONE;
|
||||||
|
|
||||||
|
public static final int TimeZoneId = REFERENCE_DATATYPE_TIMEZONE;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* - New Display Type
|
* - New Display Type
|
||||||
INSERT INTO AD_REFERENCE
|
INSERT INTO AD_REFERENCE
|
||||||
|
@ -317,7 +324,8 @@ public final class DisplayType
|
||||||
|| displayType == RadiogroupList
|
|| displayType == RadiogroupList
|
||||||
|| displayType == ChosenMultipleSelectionList
|
|| displayType == ChosenMultipleSelectionList
|
||||||
|| displayType == ChosenMultipleSelectionTable
|
|| displayType == ChosenMultipleSelectionTable
|
||||||
|| displayType == ChosenMultipleSelectionSearch)
|
|| displayType == ChosenMultipleSelectionSearch
|
||||||
|
|| displayType == TimeZoneId)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
||||||
|
@ -347,6 +355,9 @@ public final class DisplayType
|
||||||
if (displayType == Date || displayType == DateTime || displayType == Time)
|
if (displayType == Date || displayType == DateTime || displayType == Time)
|
||||||
return true;
|
return true;
|
||||||
|
|
||||||
|
if (isTimestampWithTimeZone(displayType))
|
||||||
|
return true;
|
||||||
|
|
||||||
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
||||||
if (cache != null) {
|
if (cache != null) {
|
||||||
IDisplayTypeFactory service = cache.getService();
|
IDisplayTypeFactory service = cache.getService();
|
||||||
|
@ -455,6 +466,19 @@ public final class DisplayType
|
||||||
return false;
|
return false;
|
||||||
} // isLOB
|
} // isLOB
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param displayType
|
||||||
|
* @return true if displayType == TimestampWithTimeZone
|
||||||
|
*/
|
||||||
|
public static boolean isTimestampWithTimeZone(int displayType)
|
||||||
|
{
|
||||||
|
if (displayType == TimestampWithTimeZone)
|
||||||
|
return true;
|
||||||
|
else
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
/**************************************************************************
|
/**************************************************************************
|
||||||
* Return Format for numeric DisplayType
|
* Return Format for numeric DisplayType
|
||||||
* @param displayType Display Type (default Number)
|
* @param displayType Display Type (default Number)
|
||||||
|
@ -611,8 +635,8 @@ public final class DisplayType
|
||||||
{
|
{
|
||||||
SimpleDateFormat format = (SimpleDateFormat)DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT, language.getLocale());
|
SimpleDateFormat format = (SimpleDateFormat)DateFormat.getDateTimeInstance(DateFormat.SHORT, DateFormat.SHORT, language.getLocale());
|
||||||
try {
|
try {
|
||||||
format.applyPattern(pattern);
|
format.applyPattern(pattern);
|
||||||
return format;
|
return displayType==TimeZoneId ? setTimeZone(format) : format;
|
||||||
}
|
}
|
||||||
catch (IllegalArgumentException e) {
|
catch (IllegalArgumentException e) {
|
||||||
s_log.log(Level.WARNING, "Invalid date pattern: " + pattern);
|
s_log.log(Level.WARNING, "Invalid date pattern: " + pattern);
|
||||||
|
@ -631,7 +655,14 @@ public final class DisplayType
|
||||||
return new SimpleDateFormat(lang.getTimePattern());
|
return new SimpleDateFormat(lang.getTimePattern());
|
||||||
return myLanguage.getTimeFormat();
|
return myLanguage.getTimeFormat();
|
||||||
}
|
}
|
||||||
|
else if ( displayType == TimestampWithTimeZone) {
|
||||||
|
SimpleDateFormat format = null;
|
||||||
|
if (!Util.isEmpty(lang.getDatePattern()) && !Util.isEmpty(lang.getTimePattern()))
|
||||||
|
format = new SimpleDateFormat(lang.getDatePattern() + " " + lang.getTimePattern());
|
||||||
|
else
|
||||||
|
format = myLanguage.getDateTimeFormat();
|
||||||
|
return setTimeZone(format);
|
||||||
|
}
|
||||||
else {
|
else {
|
||||||
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
IServiceReferenceHolder<IDisplayTypeFactory> cache = s_displayTypeFactoryCache.get(displayType);
|
||||||
if (cache != null) {
|
if (cache != null) {
|
||||||
|
@ -658,6 +689,20 @@ public final class DisplayType
|
||||||
return myLanguage.getDateFormat(); // default
|
return myLanguage.getDateFormat(); // default
|
||||||
} // getDateFormat
|
} // getDateFormat
|
||||||
|
|
||||||
|
private static SimpleDateFormat setTimeZone(SimpleDateFormat dateFormat) {
|
||||||
|
String timezoneId = Env.getContext(Env.getCtx(), Env.CLIENT_INFO_TIME_ZONE);
|
||||||
|
if (!Util.isEmpty(timezoneId, true))
|
||||||
|
{
|
||||||
|
TimeZone tz = TimeZone.getTimeZone(timezoneId);
|
||||||
|
if (tz != null && timezoneId.equals(tz.getID()))
|
||||||
|
{
|
||||||
|
dateFormat = new SimpleDateFormat(dateFormat.toPattern());
|
||||||
|
dateFormat.setTimeZone(tz);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
return dateFormat;
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* JDBC Date Format YYYY-MM-DD
|
* JDBC Date Format YYYY-MM-DD
|
||||||
* @return date format
|
* @return date format
|
||||||
|
@ -768,6 +813,8 @@ public final class DisplayType
|
||||||
//
|
//
|
||||||
if (displayType == DisplayType.Integer)
|
if (displayType == DisplayType.Integer)
|
||||||
return getDatabase().getNumericDataType()+"(10)";
|
return getDatabase().getNumericDataType()+"(10)";
|
||||||
|
if (DisplayType.isTimestampWithTimeZone(displayType))
|
||||||
|
return getDatabase().getTimestampWithTimezoneDataType();
|
||||||
if (DisplayType.isDate(displayType))
|
if (DisplayType.isDate(displayType))
|
||||||
return getDatabase().getTimestampDataType();
|
return getDatabase().getTimestampDataType();
|
||||||
if (DisplayType.isNumeric(displayType))
|
if (DisplayType.isNumeric(displayType))
|
||||||
|
|
|
@ -102,6 +102,11 @@ public final class Env
|
||||||
public static final String C_TAXCATEGORY_ID = "#C_TaxCategory_ID";
|
public static final String C_TAXCATEGORY_ID = "#C_TaxCategory_ID";
|
||||||
public static final String C_TAX_ID = "#C_Tax_ID";
|
public static final String C_TAX_ID = "#C_Tax_ID";
|
||||||
public static final String C_UOM_ID = "#C_UOM_ID";
|
public static final String C_UOM_ID = "#C_UOM_ID";
|
||||||
|
public static final String CLIENT_INFO_DESKTOP_HEIGHT = "#clientInfo_desktopHeight";
|
||||||
|
public static final String CLIENT_INFO_DESKTOP_WIDTH = "#clientInfo_desktopWidth";
|
||||||
|
public static final String CLIENT_INFO_MOBILE = "#clientInfo_mobile";
|
||||||
|
public static final String CLIENT_INFO_ORIENTATION = "#clientInfo_orientation";
|
||||||
|
public static final String CLIENT_INFO_TIME_ZONE = "#clientInfo_timeZone";
|
||||||
public static final String DATE = "#Date";
|
public static final String DATE = "#Date";
|
||||||
public static final String DB_TYPE = "#DBType";
|
public static final String DB_TYPE = "#DBType";
|
||||||
public static final String GL_CATEGORY_ID = "#GL_Category_ID";
|
public static final String GL_CATEGORY_ID = "#GL_Category_ID";
|
||||||
|
|
|
@ -543,17 +543,16 @@ public class TimeUtil
|
||||||
long hours = elapsedMS%24;
|
long hours = elapsedMS%24;
|
||||||
long days = elapsedMS / 24;
|
long days = elapsedMS / 24;
|
||||||
//
|
//
|
||||||
if (days != 0)
|
sb.append(days).append("'");
|
||||||
sb.append(days).append("'");
|
|
||||||
// hh
|
// hh
|
||||||
if (hours != 0)
|
if (hours != 0)
|
||||||
sb.append(get2digits(hours)).append(":");
|
sb.append(get2digits(hours)).append(":");
|
||||||
else if (days != 0)
|
else
|
||||||
sb.append("00:");
|
sb.append("00:");
|
||||||
// mm
|
// mm
|
||||||
if (minutes != 0)
|
if (minutes != 0)
|
||||||
sb.append(get2digits(minutes)).append(":");
|
sb.append(get2digits(minutes)).append(":");
|
||||||
else if (hours != 0 || days != 0)
|
else
|
||||||
sb.append("00:");
|
sb.append("00:");
|
||||||
// ss
|
// ss
|
||||||
sb.append(get2digits(seconds))
|
sb.append(get2digits(seconds))
|
||||||
|
|
|
@ -24,6 +24,7 @@ import java.util.Properties;
|
||||||
import org.compiere.model.AdempiereProcessor;
|
import org.compiere.model.AdempiereProcessor;
|
||||||
import org.compiere.model.AdempiereProcessor2;
|
import org.compiere.model.AdempiereProcessor2;
|
||||||
import org.compiere.model.AdempiereProcessorLog;
|
import org.compiere.model.AdempiereProcessorLog;
|
||||||
|
import org.compiere.model.MClientInfo;
|
||||||
import org.compiere.model.MSchedule;
|
import org.compiere.model.MSchedule;
|
||||||
import org.compiere.model.Query;
|
import org.compiere.model.Query;
|
||||||
import org.compiere.model.X_AD_WorkflowProcessor;
|
import org.compiere.model.X_AD_WorkflowProcessor;
|
||||||
|
@ -142,7 +143,8 @@ public class MWorkflowProcessor extends X_AD_WorkflowProcessor
|
||||||
protected boolean beforeSave(boolean newRecord)
|
protected boolean beforeSave(boolean newRecord)
|
||||||
{
|
{
|
||||||
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
if (newRecord || is_ValueChanged("AD_Schedule_ID")) {
|
||||||
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern());
|
long nextWork = MSchedule.getNextRunMS(System.currentTimeMillis(), getScheduleType(), getFrequencyType(), getFrequency(), getCronPattern(),
|
||||||
|
MClientInfo.get(getCtx(), getAD_Client_ID()).getTimeZone());
|
||||||
if (nextWork > 0)
|
if (nextWork > 0)
|
||||||
setDateNextRun(new Timestamp(nextWork));
|
setDateNextRun(new Timestamp(nextWork));
|
||||||
}
|
}
|
||||||
|
|
|
@ -26,6 +26,7 @@ import org.compiere.model.AdempiereProcessor;
|
||||||
import org.compiere.model.AdempiereProcessor2;
|
import org.compiere.model.AdempiereProcessor2;
|
||||||
import org.compiere.model.AdempiereProcessorLog;
|
import org.compiere.model.AdempiereProcessorLog;
|
||||||
import org.compiere.model.MClient;
|
import org.compiere.model.MClient;
|
||||||
|
import org.compiere.model.MClientInfo;
|
||||||
import org.compiere.model.MOrgInfo;
|
import org.compiere.model.MOrgInfo;
|
||||||
import org.compiere.model.MRole;
|
import org.compiere.model.MRole;
|
||||||
import org.compiere.model.MSchedule;
|
import org.compiere.model.MSchedule;
|
||||||
|
@ -127,7 +128,7 @@ public abstract class AdempiereServer implements Runnable
|
||||||
{
|
{
|
||||||
m_nextWork = MSchedule.getNextRunMS(now.getTime(),
|
m_nextWork = MSchedule.getNextRunMS(now.getTime(),
|
||||||
p_model.getScheduleType(), p_model.getFrequencyType(),
|
p_model.getScheduleType(), p_model.getFrequencyType(),
|
||||||
p_model.getFrequency(), p_model.getCronPattern());
|
p_model.getFrequency(), p_model.getCronPattern(), MClientInfo.get(getCtx(), p_model.getAD_Client_ID()).getTimeZone());
|
||||||
}
|
}
|
||||||
|
|
||||||
if (m_nextWork > now.getTime())
|
if (m_nextWork > now.getTime())
|
||||||
|
@ -294,7 +295,7 @@ public abstract class AdempiereServer implements Runnable
|
||||||
|
|
||||||
m_nextWork = MSchedule.getNextRunMS(lastRun.getTime(),
|
m_nextWork = MSchedule.getNextRunMS(lastRun.getTime(),
|
||||||
p_model.getScheduleType(), p_model.getFrequencyType(),
|
p_model.getScheduleType(), p_model.getFrequencyType(),
|
||||||
p_model.getFrequency(), p_model.getCronPattern());
|
p_model.getFrequency(), p_model.getCronPattern(), MClientInfo.get(getCtx(), p_model.getAD_Client_ID()).getTimeZone());
|
||||||
|
|
||||||
m_sleepMS = m_nextWork - now;
|
m_sleepMS = m_nextWork - now;
|
||||||
if (m_nextWork == 0) {
|
if (m_nextWork == 0) {
|
||||||
|
|
|
@ -24,10 +24,14 @@ import java.io.IOException;
|
||||||
import java.io.PrintWriter;
|
import java.io.PrintWriter;
|
||||||
import java.net.InetAddress;
|
import java.net.InetAddress;
|
||||||
import java.sql.Timestamp;
|
import java.sql.Timestamp;
|
||||||
|
import java.time.ZoneId;
|
||||||
|
import java.time.format.DateTimeFormatter;
|
||||||
|
import java.time.temporal.ChronoUnit;
|
||||||
import java.util.ArrayList;
|
import java.util.ArrayList;
|
||||||
|
|
||||||
import java.util.Arrays;
|
import java.util.Arrays;
|
||||||
import java.util.Comparator;
|
import java.util.Comparator;
|
||||||
|
import java.util.Date;
|
||||||
import java.util.Collection;
|
import java.util.Collection;
|
||||||
import java.util.List;
|
import java.util.List;
|
||||||
import java.util.Properties;
|
import java.util.Properties;
|
||||||
|
@ -65,6 +69,7 @@ import org.apache.ecs.xhtml.tr;
|
||||||
import org.compiere.Adempiere;
|
import org.compiere.Adempiere;
|
||||||
import org.compiere.model.AdempiereProcessorLog;
|
import org.compiere.model.AdempiereProcessorLog;
|
||||||
import org.compiere.model.MClient;
|
import org.compiere.model.MClient;
|
||||||
|
import org.compiere.model.MClientInfo;
|
||||||
import org.compiere.model.MSession;
|
import org.compiere.model.MSession;
|
||||||
import org.compiere.model.MSysConfig;
|
import org.compiere.model.MSysConfig;
|
||||||
import org.compiere.model.MSystem;
|
import org.compiere.model.MSystem;
|
||||||
|
@ -687,7 +692,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Start - Elapsed"));
|
line.addElement(new th().addElement("Start - Elapsed"));
|
||||||
line.addElement(new td().addElement(WebEnv.getCellContent(getServerManager().getStartTime())
|
line.addElement(new td().addElement(WebEnv.getCellContent(formatTimestampWithTimeZone(0, getServerManager().getStartTime()))
|
||||||
+ " - " + TimeUtil.formatElapsed(getServerManager().getStartTime())));
|
+ " - " + TimeUtil.formatElapsed(getServerManager().getStartTime())));
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
line = new tr();
|
line = new tr();
|
||||||
|
@ -696,7 +701,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Last Updated"));
|
line.addElement(new th().addElement("Last Updated"));
|
||||||
line.addElement(new td().addElement(new Timestamp(System.currentTimeMillis()).toString()));
|
line.addElement(new td().addElement(formatTimestampWithTimeZone(0, new Timestamp(System.currentTimeMillis()))));
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
bb.addElement(table);
|
bb.addElement(table);
|
||||||
|
|
||||||
|
@ -834,7 +839,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Start - Elapsed"));
|
line.addElement(new th().addElement("Start - Elapsed"));
|
||||||
line.addElement(new td().addElement(WebEnv.getCellContent(server.getStartTime())
|
line.addElement(new td().addElement(WebEnv.getCellContent(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getStartTime()))
|
||||||
+ " - " + TimeUtil.formatElapsed(server.getStartTime())));
|
+ " - " + TimeUtil.formatElapsed(server.getStartTime())));
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
|
@ -853,7 +858,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
//
|
//
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Last Run"));
|
line.addElement(new th().addElement("Last Run"));
|
||||||
line.addElement(new td().addElement(WebEnv.getCellContent(server.getModel().getDateLastRun())));
|
line.addElement(new td().addElement(WebEnv.getCellContent(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getModel().getDateLastRun()))));
|
||||||
table.addElement(line);
|
table.addElement(line);
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Info"));
|
line.addElement(new th().addElement("Info"));
|
||||||
|
@ -863,7 +868,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
line = new tr();
|
line = new tr();
|
||||||
line.addElement(new th().addElement("Next Run"));
|
line.addElement(new th().addElement("Next Run"));
|
||||||
td td = new td();
|
td td = new td();
|
||||||
td.addElement(WebEnv.getCellContent(server.getModel().getDateNextRun(false)));
|
td.addElement(WebEnv.getCellContent(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getModel().getDateNextRun(false))));
|
||||||
td.addElement(" - ");
|
td.addElement(" - ");
|
||||||
link = new a ("idempiereMonitor?RunNow=" + server.getServerId(), "(Run Now)");
|
link = new a ("idempiereMonitor?RunNow=" + server.getServerId(), "(Run Now)");
|
||||||
td.addElement(link);
|
td.addElement(link);
|
||||||
|
@ -912,6 +917,22 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
WebUtil.createResponse (request, response, this, null, doc, false);
|
WebUtil.createResponse (request, response, this, null, doc, false);
|
||||||
} // createSummaryPage
|
} // createSummaryPage
|
||||||
|
|
||||||
|
private String formatTimestampWithTimeZone(int AD_Client_ID, Timestamp ts) {
|
||||||
|
return formatTimestampWithTimeZone(AD_Client_ID, (Date)ts);
|
||||||
|
}
|
||||||
|
|
||||||
|
private String formatTimestampWithTimeZone(int AD_Client_ID, Date date) {
|
||||||
|
if (date == null)
|
||||||
|
return "";
|
||||||
|
DateTimeFormatter formatter = DateTimeFormatter.ISO_ZONED_DATE_TIME;
|
||||||
|
MClientInfo clientInfo = MClientInfo.get(AD_Client_ID);
|
||||||
|
if (!Util.isEmpty(clientInfo.getTimeZone()))
|
||||||
|
formatter = formatter.withZone(ZoneId.of(clientInfo.getTimeZone()));
|
||||||
|
else
|
||||||
|
formatter = formatter.withZone(ZoneId.systemDefault());
|
||||||
|
return formatter.format(date.toInstant().truncatedTo(ChronoUnit.SECONDS));
|
||||||
|
}
|
||||||
|
|
||||||
private String createServerCountMessage(ServerCount serverCount) {
|
private String createServerCountMessage(ServerCount serverCount) {
|
||||||
StringBuilder builder = new StringBuilder();
|
StringBuilder builder = new StringBuilder();
|
||||||
|
|
||||||
|
@ -971,7 +992,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
writer.print(getServerManager().getDescription());
|
writer.print(getServerManager().getDescription());
|
||||||
writer.println("</description>");
|
writer.println("</description>");
|
||||||
writer.print("\t\t<start-time>");
|
writer.print("\t\t<start-time>");
|
||||||
writer.print(getServerManager().getStartTime());
|
writer.print(formatTimestampWithTimeZone(0, getServerManager().getStartTime()));
|
||||||
writer.println("</start-time>");
|
writer.println("</start-time>");
|
||||||
writer.print("\t\t<server-count>");
|
writer.print("\t\t<server-count>");
|
||||||
writer.print(getServerManager().getServerCount());
|
writer.print(getServerManager().getServerCount());
|
||||||
|
@ -1008,13 +1029,13 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
writer.print("Stopped");
|
writer.print("Stopped");
|
||||||
writer.println("</status>");
|
writer.println("</status>");
|
||||||
writer.print("\t\t\t<start-time>");
|
writer.print("\t\t\t<start-time>");
|
||||||
writer.print(server.getStartTime());
|
writer.print(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getStartTime()));
|
||||||
writer.println("</start-time>");
|
writer.println("</start-time>");
|
||||||
writer.print("\t\t\t<last-run>");
|
writer.print("\t\t\t<last-run>");
|
||||||
writer.print(server.getModel().getDateLastRun());
|
writer.print(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getModel().getDateLastRun()));
|
||||||
writer.println("</last-run>");
|
writer.println("</last-run>");
|
||||||
writer.print("\t\t\t<next-run>");
|
writer.print("\t\t\t<next-run>");
|
||||||
writer.print(server.getModel().getDateNextRun(false));
|
writer.print(formatTimestampWithTimeZone(server.getModel().getAD_Client_ID(), server.getModel().getDateNextRun(false)));
|
||||||
writer.println("</next-run>");
|
writer.println("</next-run>");
|
||||||
writer.print("\t\t\t<statistics>");
|
writer.print("\t\t\t<statistics>");
|
||||||
writer.print(server.getStatistics());
|
writer.print(server.getStatistics());
|
||||||
|
@ -1115,7 +1136,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
td td = new td();
|
td td = new td();
|
||||||
td.setOnClick("var newwindow=window.open('','Popup', 'width=800,height=600');newwindow.document.write('<title>" + escapeEcmaScript(trx.getDisplayName()) +"</title>"
|
td.setOnClick("var newwindow=window.open('','Popup', 'width=800,height=600');newwindow.document.write('<title>" + escapeEcmaScript(trx.getDisplayName()) +"</title>"
|
||||||
+ "<pre>" + escapeEcmaScript(trx.getStackTrace()) + "</pre>')");
|
+ "<pre>" + escapeEcmaScript(trx.getStackTrace()) + "</pre>')");
|
||||||
td.addElement("Name="+trx.getDisplayName() + ", StartTime=" + trx.getStartTime());
|
td.addElement("Name="+trx.getDisplayName() + ", StartTime=" + formatTimestampWithTimeZone(0,trx.getStartTime()));
|
||||||
td.setTitle("Click to see stack trace");
|
td.setTitle("Click to see stack trace");
|
||||||
td.setStyle("text-decoration: underline; color: blue");
|
td.setStyle("text-decoration: underline; color: blue");
|
||||||
line.addElement(td);
|
line.addElement(td);
|
||||||
|
@ -1692,7 +1713,7 @@ public class AdempiereMonitor extends HttpServlet
|
||||||
td td = new td();
|
td td = new td();
|
||||||
td.setOnClick("var newwindow=window.open('','Popup', 'width=800,height=600');newwindow.document.write('<title>" + escapeEcmaScript(trx.getDisplayName()) +"</title>"
|
td.setOnClick("var newwindow=window.open('','Popup', 'width=800,height=600');newwindow.document.write('<title>" + escapeEcmaScript(trx.getDisplayName()) +"</title>"
|
||||||
+ "<pre>" + escapeEcmaScript(trx.getStackTrace()) + "</pre>')");
|
+ "<pre>" + escapeEcmaScript(trx.getStackTrace()) + "</pre>')");
|
||||||
td.addElement("Name="+trx.getDisplayName() + ", StartTime=" + trx.getStartTime());
|
td.addElement("Name="+trx.getDisplayName() + ", StartTime=" + formatTimestampWithTimeZone(0, trx.getStartTime()));
|
||||||
td.setTitle("Click to see stack trace");
|
td.setTitle("Click to see stack trace");
|
||||||
td.setStyle("text-decoration: underline; color: blue");
|
td.setStyle("text-decoration: underline; color: blue");
|
||||||
line.addElement(td);
|
line.addElement(td);
|
||||||
|
|
|
@ -535,15 +535,16 @@ public class AdempiereWebUI extends Window implements EventListener<Event>, IWeb
|
||||||
Executions.getCurrent().getSession().setAttribute(CLIENT_INFO, clientInfo);
|
Executions.getCurrent().getSession().setAttribute(CLIENT_INFO, clientInfo);
|
||||||
}
|
}
|
||||||
|
|
||||||
Env.setContext(Env.getCtx(), "#clientInfo_desktopWidth", clientInfo.desktopWidth);
|
Env.setContext(Env.getCtx(), Env.CLIENT_INFO_DESKTOP_WIDTH, clientInfo.desktopWidth);
|
||||||
Env.setContext(Env.getCtx(), "#clientInfo_desktopHeight", clientInfo.desktopHeight);
|
Env.setContext(Env.getCtx(), Env.CLIENT_INFO_DESKTOP_HEIGHT, clientInfo.desktopHeight);
|
||||||
Env.setContext(Env.getCtx(), "#clientInfo_orientation", clientInfo.orientation);
|
Env.setContext(Env.getCtx(), Env.CLIENT_INFO_ORIENTATION, clientInfo.orientation);
|
||||||
Env.setContext(Env.getCtx(), "#clientInfo_mobile", clientInfo.tablet);
|
Env.setContext(Env.getCtx(), Env.CLIENT_INFO_MOBILE, clientInfo.tablet);
|
||||||
|
if (clientInfo.timeZone != null)
|
||||||
|
Env.setContext(Env.getCtx(), Env.CLIENT_INFO_TIME_ZONE, clientInfo.timeZone.getID());
|
||||||
|
|
||||||
IDesktop appDesktop = getAppDeskop();
|
IDesktop appDesktop = getAppDeskop();
|
||||||
if (appDesktop != null)
|
if (appDesktop != null)
|
||||||
appDesktop.setClientInfo(clientInfo);
|
appDesktop.setClientInfo(clientInfo);
|
||||||
|
|
||||||
} else if (event.getName().equals(ON_LOGIN_COMPLETED)) {
|
} else if (event.getName().equals(ON_LOGIN_COMPLETED)) {
|
||||||
loginCompleted();
|
loginCompleted();
|
||||||
}
|
}
|
||||||
|
@ -601,10 +602,11 @@ public class AdempiereWebUI extends Window implements EventListener<Event>, IWeb
|
||||||
Env.setContext(properties, ITheme.ZK_TOOLBAR_BUTTON_SIZE, Env.getContext(Env.getCtx(), ITheme.ZK_TOOLBAR_BUTTON_SIZE));
|
Env.setContext(properties, ITheme.ZK_TOOLBAR_BUTTON_SIZE, Env.getContext(Env.getCtx(), ITheme.ZK_TOOLBAR_BUTTON_SIZE));
|
||||||
Env.setContext(properties, ITheme.USE_CSS_FOR_WINDOW_SIZE, Env.getContext(Env.getCtx(), ITheme.USE_CSS_FOR_WINDOW_SIZE));
|
Env.setContext(properties, ITheme.USE_CSS_FOR_WINDOW_SIZE, Env.getContext(Env.getCtx(), ITheme.USE_CSS_FOR_WINDOW_SIZE));
|
||||||
Env.setContext(properties, ITheme.USE_FONT_ICON_FOR_IMAGE, Env.getContext(Env.getCtx(), ITheme.USE_FONT_ICON_FOR_IMAGE));
|
Env.setContext(properties, ITheme.USE_FONT_ICON_FOR_IMAGE, Env.getContext(Env.getCtx(), ITheme.USE_FONT_ICON_FOR_IMAGE));
|
||||||
Env.setContext(properties, "#clientInfo_desktopWidth", clientInfo.desktopWidth);
|
Env.setContext(properties, Env.CLIENT_INFO_DESKTOP_WIDTH, clientInfo.desktopWidth);
|
||||||
Env.setContext(properties, "#clientInfo_desktopHeight", clientInfo.desktopHeight);
|
Env.setContext(properties, Env.CLIENT_INFO_DESKTOP_HEIGHT, clientInfo.desktopHeight);
|
||||||
Env.setContext(properties, "#clientInfo_orientation", clientInfo.orientation);
|
Env.setContext(properties, Env.CLIENT_INFO_ORIENTATION, clientInfo.orientation);
|
||||||
Env.setContext(properties, "#clientInfo_mobile", clientInfo.tablet);
|
Env.setContext(properties, Env.CLIENT_INFO_MOBILE, clientInfo.tablet);
|
||||||
|
Env.setContext(properties, Env.CLIENT_INFO_TIME_ZONE, clientInfo.timeZone.getID());
|
||||||
|
|
||||||
Desktop desktop = Executions.getCurrent().getDesktop();
|
Desktop desktop = Executions.getCurrent().getDesktop();
|
||||||
Locale locale = (Locale) desktop.getSession().getAttribute(Attributes.PREFERRED_LOCALE);
|
Locale locale = (Locale) desktop.getSession().getAttribute(Attributes.PREFERRED_LOCALE);
|
||||||
|
|
|
@ -96,7 +96,7 @@ public class ClientInfo implements Serializable {
|
||||||
* @return true if mobile browser
|
* @return true if mobile browser
|
||||||
*/
|
*/
|
||||||
public static boolean isMobile() {
|
public static boolean isMobile() {
|
||||||
return "Y".equals(Env.getContext(Env.getCtx(), "#clientInfo_mobile"));
|
return "Y".equals(Env.getContext(Env.getCtx(), Env.CLIENT_INFO_MOBILE));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|
|
@ -13,8 +13,11 @@
|
||||||
package org.adempiere.webui.component;
|
package org.adempiere.webui.component;
|
||||||
|
|
||||||
import java.text.SimpleDateFormat;
|
import java.text.SimpleDateFormat;
|
||||||
|
import java.time.LocalDateTime;
|
||||||
|
import java.time.ZonedDateTime;
|
||||||
import java.util.Calendar;
|
import java.util.Calendar;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
import java.util.TimeZone;
|
||||||
|
|
||||||
import org.zkoss.zk.ui.event.EventListener;
|
import org.zkoss.zk.ui.event.EventListener;
|
||||||
|
|
||||||
|
@ -31,13 +34,13 @@ public class DatetimeBox extends Panel {
|
||||||
private static final long serialVersionUID = -1075410511739601354L;
|
private static final long serialVersionUID = -1075410511739601354L;
|
||||||
private Datebox dateBox;
|
private Datebox dateBox;
|
||||||
private Timebox timeBox;
|
private Timebox timeBox;
|
||||||
|
private TimeZone timeZone;
|
||||||
|
|
||||||
public DatetimeBox() {
|
public DatetimeBox() {
|
||||||
dateBox = new Datebox();
|
dateBox = new Datebox();
|
||||||
dateBox.setCols(10);
|
dateBox.setCols(10);
|
||||||
timeBox = new Timebox();
|
timeBox = new Timebox();
|
||||||
timeBox.setCols(10);
|
timeBox.setCols(10);
|
||||||
//timeBox.setButtonVisible(false);
|
|
||||||
appendChild(dateBox);
|
appendChild(dateBox);
|
||||||
appendChild(timeBox);
|
appendChild(timeBox);
|
||||||
|
|
||||||
|
@ -107,17 +110,40 @@ public class DatetimeBox extends Panel {
|
||||||
* @return date
|
* @return date
|
||||||
*/
|
*/
|
||||||
public Date getValue() {
|
public Date getValue() {
|
||||||
Date d = dateBox.getValue();
|
Date d = null;
|
||||||
Date t = timeBox.getValue();
|
if (timeZone != null) {
|
||||||
|
ZonedDateTime zonedDate = dateBox.getValueInZonedDateTime();
|
||||||
|
if (zonedDate != null)
|
||||||
|
d = Date.from(zonedDate.toInstant().atZone(timeZone.toZoneId()).toInstant());
|
||||||
|
Date t = null;
|
||||||
|
ZonedDateTime zonedTime = timeBox.getValueInZonedDateTime();
|
||||||
|
if (zonedTime != null)
|
||||||
|
t = Date.from(zonedTime.toInstant().atZone(timeZone.toZoneId()).toInstant());
|
||||||
|
|
||||||
if (d != null && t != null) {
|
if (d != null && t != null) {
|
||||||
Calendar cd = Calendar.getInstance();
|
Calendar cd = Calendar.getInstance();
|
||||||
cd.setTime(d);
|
cd.setTimeZone(dateBox.getTimeZone());
|
||||||
Calendar ct = Calendar.getInstance();
|
cd.setTime(d);
|
||||||
ct.setTime(t);
|
Calendar ct = Calendar.getInstance();
|
||||||
cd.set(cd.get(Calendar.YEAR), cd.get(Calendar.MONTH), cd.get(Calendar.DAY_OF_MONTH),
|
ct.setTimeZone(timeBox.getTimeZone());
|
||||||
ct.get(Calendar.HOUR_OF_DAY), ct.get(Calendar.MINUTE), ct.get(Calendar.SECOND));
|
ct.setTime(t);
|
||||||
d = cd.getTime();
|
cd.set(cd.get(Calendar.YEAR), cd.get(Calendar.MONTH), cd.get(Calendar.DAY_OF_MONTH),
|
||||||
|
ct.get(Calendar.HOUR_OF_DAY), ct.get(Calendar.MINUTE), ct.get(Calendar.SECOND));
|
||||||
|
d = cd.getTime();
|
||||||
|
}
|
||||||
|
} else {
|
||||||
|
d = dateBox.getValue();
|
||||||
|
Date t = timeBox.getValue();
|
||||||
|
|
||||||
|
if (d != null && t != null) {
|
||||||
|
Calendar cd = Calendar.getInstance();
|
||||||
|
cd.setTime(d);
|
||||||
|
Calendar ct = Calendar.getInstance();
|
||||||
|
ct.setTime(t);
|
||||||
|
cd.set(cd.get(Calendar.YEAR), cd.get(Calendar.MONTH), cd.get(Calendar.DAY_OF_MONTH),
|
||||||
|
ct.get(Calendar.HOUR_OF_DAY), ct.get(Calendar.MINUTE), ct.get(Calendar.SECOND));
|
||||||
|
d = cd.getTime();
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return d;
|
return d;
|
||||||
|
@ -146,4 +172,36 @@ public class DatetimeBox extends Panel {
|
||||||
{
|
{
|
||||||
return timeBox;
|
return timeBox;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param tz
|
||||||
|
*/
|
||||||
|
public void setTimeZone(TimeZone tz) {
|
||||||
|
this.timeZone = tz;
|
||||||
|
dateBox.setTimeZone(tz);
|
||||||
|
timeBox.setTimeZone(tz);
|
||||||
|
if (tz == null)
|
||||||
|
timeBox.setCols(10);
|
||||||
|
else
|
||||||
|
timeBox.setCols(14);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param localTime
|
||||||
|
*/
|
||||||
|
public void setValueInLocalDateTime(LocalDateTime localTime) {
|
||||||
|
dateBox.setValueInLocalDateTime(localTime);
|
||||||
|
timeBox.setValueInLocalDateTime(localTime);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param zdt
|
||||||
|
*/
|
||||||
|
public void setValueInZonedDateTime(ZonedDateTime zdt) {
|
||||||
|
dateBox.setValueInZonedDateTime(zdt);
|
||||||
|
timeBox.setValueInZonedDateTime(zdt);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -15,7 +15,9 @@ package org.adempiere.webui.editor;
|
||||||
import java.sql.Timestamp;
|
import java.sql.Timestamp;
|
||||||
import java.time.LocalDateTime;
|
import java.time.LocalDateTime;
|
||||||
import java.time.ZoneId;
|
import java.time.ZoneId;
|
||||||
|
import java.time.ZonedDateTime;
|
||||||
import java.util.Date;
|
import java.util.Date;
|
||||||
|
import java.util.TimeZone;
|
||||||
|
|
||||||
import org.adempiere.webui.ValuePreference;
|
import org.adempiere.webui.ValuePreference;
|
||||||
import org.adempiere.webui.component.DatetimeBox;
|
import org.adempiere.webui.component.DatetimeBox;
|
||||||
|
@ -24,9 +26,12 @@ import org.adempiere.webui.event.ContextMenuListener;
|
||||||
import org.adempiere.webui.event.ValueChangeEvent;
|
import org.adempiere.webui.event.ValueChangeEvent;
|
||||||
import org.adempiere.webui.window.WFieldRecordInfo;
|
import org.adempiere.webui.window.WFieldRecordInfo;
|
||||||
import org.compiere.model.GridField;
|
import org.compiere.model.GridField;
|
||||||
|
import org.compiere.model.MClientInfo;
|
||||||
import org.compiere.util.CLogger;
|
import org.compiere.util.CLogger;
|
||||||
|
import org.compiere.util.DisplayType;
|
||||||
import org.compiere.util.Env;
|
import org.compiere.util.Env;
|
||||||
import org.compiere.util.Msg;
|
import org.compiere.util.Msg;
|
||||||
|
import org.compiere.util.Util;
|
||||||
import org.zkoss.zk.ui.event.Event;
|
import org.zkoss.zk.ui.event.Event;
|
||||||
import org.zkoss.zk.ui.event.Events;
|
import org.zkoss.zk.ui.event.Events;
|
||||||
|
|
||||||
|
@ -115,8 +120,37 @@ public class WDatetimeEditor extends WEditor implements ContextMenuListener
|
||||||
addChangeLogMenu(popupMenu);
|
addChangeLogMenu(popupMenu);
|
||||||
if (gridField != null)
|
if (gridField != null)
|
||||||
getComponent().getDatebox().setPlaceholder(gridField.getPlaceholder());
|
getComponent().getDatebox().setPlaceholder(gridField.getPlaceholder());
|
||||||
|
|
||||||
|
if (isTimestampWithTimeZone())
|
||||||
|
{
|
||||||
|
MClientInfo clientInfo = MClientInfo.get();
|
||||||
|
String timezoneId = clientInfo.getTimeZone();
|
||||||
|
if (Util.isEmpty(timezoneId, true))
|
||||||
|
timezoneId = Env.getContext(Env.getCtx(), Env.CLIENT_INFO_TIME_ZONE);
|
||||||
|
|
||||||
|
if (!Util.isEmpty(timezoneId, true))
|
||||||
|
{
|
||||||
|
TimeZone tz = TimeZone.getTimeZone(timezoneId);
|
||||||
|
if (tz != null && timezoneId.equals(tz.getID()))
|
||||||
|
{
|
||||||
|
getComponent().setTimeZone(tz);
|
||||||
|
getComponent().getTimebox().setFormat("hh:mm:ss a z");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private boolean isTimestampWithTimeZone()
|
||||||
|
{
|
||||||
|
if (gridField != null)
|
||||||
|
{
|
||||||
|
int displayType = gridField.getDisplayType();
|
||||||
|
return DisplayType.isTimestampWithTimeZone(displayType);
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
public void onEvent(Event event)
|
public void onEvent(Event event)
|
||||||
{
|
{
|
||||||
if (Events.ON_CHANGE.equalsIgnoreCase(event.getName()) || Events.ON_OK.equalsIgnoreCase(event.getName()))
|
if (Events.ON_CHANGE.equalsIgnoreCase(event.getName()) || Events.ON_OK.equalsIgnoreCase(event.getName()))
|
||||||
|
@ -126,7 +160,14 @@ public class WDatetimeEditor extends WEditor implements ContextMenuListener
|
||||||
|
|
||||||
if (date != null)
|
if (date != null)
|
||||||
{
|
{
|
||||||
newValue = Timestamp.valueOf(date.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime());
|
if (isTimestampWithTimeZone())
|
||||||
|
{
|
||||||
|
newValue = Timestamp.from(date.toInstant());
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
newValue = Timestamp.valueOf(date.toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime());
|
||||||
|
}
|
||||||
}
|
}
|
||||||
if (oldValue != null && newValue != null && oldValue.equals(newValue)) {
|
if (oldValue != null && newValue != null && oldValue.equals(newValue)) {
|
||||||
return;
|
return;
|
||||||
|
@ -167,10 +208,18 @@ public class WDatetimeEditor extends WEditor implements ContextMenuListener
|
||||||
}
|
}
|
||||||
else if (value instanceof Timestamp)
|
else if (value instanceof Timestamp)
|
||||||
{
|
{
|
||||||
LocalDateTime localTime =((Timestamp)value).toLocalDateTime();
|
Timestamp ts = (Timestamp) value;
|
||||||
getComponent().getDatebox().setValueInLocalDateTime(localTime);
|
if (isTimestampWithTimeZone())
|
||||||
getComponent().getTimebox().setValueInLocalDateTime(localTime);
|
{
|
||||||
oldValue = (Timestamp)value;
|
ZonedDateTime zdt = ts.toInstant().atZone(getComponent().getDatebox().getTimeZone().toZoneId());
|
||||||
|
getComponent().setValueInZonedDateTime(zdt);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
LocalDateTime localTime = ts.toLocalDateTime();
|
||||||
|
getComponent().setValueInLocalDateTime(localTime);
|
||||||
|
}
|
||||||
|
oldValue = ts;
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
|
@ -179,9 +228,16 @@ public class WDatetimeEditor extends WEditor implements ContextMenuListener
|
||||||
getComponent().setText(value.toString());
|
getComponent().setText(value.toString());
|
||||||
} catch (Exception e) {}
|
} catch (Exception e) {}
|
||||||
if (getComponent().getValue() != null)
|
if (getComponent().getValue() != null)
|
||||||
oldValue = Timestamp.valueOf(getComponent().getDatebox().getValue().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime());
|
{
|
||||||
|
if (isTimestampWithTimeZone())
|
||||||
|
oldValue = Timestamp.from(getComponent().getDatebox().getValue().toInstant());
|
||||||
|
else
|
||||||
|
oldValue = Timestamp.valueOf(getComponent().getDatebox().getValue().toInstant().atZone(ZoneId.systemDefault()).toLocalDateTime());
|
||||||
|
}
|
||||||
else
|
else
|
||||||
|
{
|
||||||
oldValue = null;
|
oldValue = null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -288,7 +288,7 @@ public class WEditorPopupMenu extends Menupopup implements EventListener<Event>
|
||||||
if (evt != null)
|
if (evt != null)
|
||||||
{
|
{
|
||||||
ContextMenuEvent menuEvent = new ContextMenuEvent(evt);
|
ContextMenuEvent menuEvent = new ContextMenuEvent(evt);
|
||||||
|
menuEvent.setTarget(event.getTarget());
|
||||||
ContextMenuListener[] listeners = new ContextMenuListener[0];
|
ContextMenuListener[] listeners = new ContextMenuListener[0];
|
||||||
listeners = menuListeners.toArray(listeners);
|
listeners = menuListeners.toArray(listeners);
|
||||||
for (ContextMenuListener listener : listeners)
|
for (ContextMenuListener listener : listeners)
|
||||||
|
|
|
@ -0,0 +1,467 @@
|
||||||
|
/***********************************************************************
|
||||||
|
* This file is part of iDempiere ERP Open Source *
|
||||||
|
* http://www.idempiere.org *
|
||||||
|
* *
|
||||||
|
* Copyright (C) Contributors *
|
||||||
|
* *
|
||||||
|
* This program is free software; you can redistribute it and/or *
|
||||||
|
* modify it under the terms of the GNU General Public License *
|
||||||
|
* as published by the Free Software Foundation; either version 2 *
|
||||||
|
* of the License, or (at your option) any later version. *
|
||||||
|
* *
|
||||||
|
* This program is distributed in the hope that it will be useful, *
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
||||||
|
* GNU General Public License for more details. *
|
||||||
|
* *
|
||||||
|
* You should have received a copy of the GNU General Public License *
|
||||||
|
* along with this program; if not, write to the Free Software *
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, *
|
||||||
|
* MA 02110-1301, USA. *
|
||||||
|
* *
|
||||||
|
* Contributors: *
|
||||||
|
* - hengsin *
|
||||||
|
**********************************************************************/
|
||||||
|
package org.adempiere.webui.editor;
|
||||||
|
|
||||||
|
import java.time.ZoneId;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Collections;
|
||||||
|
import java.util.HashMap;
|
||||||
|
import java.util.List;
|
||||||
|
import java.util.Map;
|
||||||
|
import java.util.Set;
|
||||||
|
import java.util.TimeZone;
|
||||||
|
|
||||||
|
import org.adempiere.webui.ClientInfo;
|
||||||
|
import org.adempiere.webui.ValuePreference;
|
||||||
|
import org.adempiere.webui.component.Combobox;
|
||||||
|
import org.adempiere.webui.component.Menupopup;
|
||||||
|
import org.adempiere.webui.event.ContextMenuEvent;
|
||||||
|
import org.adempiere.webui.event.ContextMenuListener;
|
||||||
|
import org.adempiere.webui.event.ValueChangeEvent;
|
||||||
|
import org.adempiere.webui.session.SessionManager;
|
||||||
|
import org.compiere.model.GridField;
|
||||||
|
import org.compiere.util.Env;
|
||||||
|
import org.compiere.util.Msg;
|
||||||
|
import org.compiere.util.NamePair;
|
||||||
|
import org.compiere.util.Util;
|
||||||
|
import org.compiere.util.ValueNamePair;
|
||||||
|
import org.zkoss.zk.ui.Component;
|
||||||
|
import org.zkoss.zk.ui.event.Event;
|
||||||
|
import org.zkoss.zk.ui.event.Events;
|
||||||
|
import org.zkoss.zul.Comboitem;
|
||||||
|
import org.zkoss.zul.Menu;
|
||||||
|
import org.zkoss.zul.Menuitem;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author hengsin
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class WTimeZoneEditor extends WEditor implements ContextMenuListener {
|
||||||
|
|
||||||
|
private static final String[] LISTENER_EVENTS = {Events.ON_CHANGE};
|
||||||
|
private static final String TIME_ZONE = "TIME_ZONE";
|
||||||
|
private static final String TIME_ZONE_ADDED = "TIME_ZONE_ADDED";
|
||||||
|
private static final String TIME_ZONE_ITEM_ATTR = "TIME_ZONE_ITEM";
|
||||||
|
private static final String TIME_ZONE_ID_ATTR = "TIME_ZONE_ID";
|
||||||
|
|
||||||
|
private String oldValue;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param gridField
|
||||||
|
*/
|
||||||
|
public WTimeZoneEditor(GridField gridField) {
|
||||||
|
this(gridField, false);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param gridField
|
||||||
|
* @param rowIndex
|
||||||
|
*/
|
||||||
|
public WTimeZoneEditor(GridField gridField, boolean tableEditor) {
|
||||||
|
super(new Combobox(), gridField);
|
||||||
|
this.tableEditor = tableEditor;
|
||||||
|
init();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param label
|
||||||
|
* @param description
|
||||||
|
* @param mandatory
|
||||||
|
* @param readonly
|
||||||
|
* @param updateable
|
||||||
|
*/
|
||||||
|
public WTimeZoneEditor(String label, String description,
|
||||||
|
boolean mandatory, boolean readonly, boolean updateable) {
|
||||||
|
super(new Combobox(), label, description, mandatory, readonly, updateable);
|
||||||
|
init();
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param columnName
|
||||||
|
* @param label
|
||||||
|
* @param description
|
||||||
|
* @param mandatory
|
||||||
|
* @param readonly
|
||||||
|
* @param updateable
|
||||||
|
*/
|
||||||
|
public WTimeZoneEditor(String columnName, String label,
|
||||||
|
String description, boolean mandatory, boolean readonly,
|
||||||
|
boolean updateable) {
|
||||||
|
super(new Combobox(), columnName, label, description, mandatory, readonly,
|
||||||
|
updateable);
|
||||||
|
init();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void init() {
|
||||||
|
popupMenu = new WEditorPopupMenu(false, false, isShowPreference());
|
||||||
|
popupMenu.addMenuListener(this);
|
||||||
|
popupMenu.addEventListener(Events.ON_OPEN, this);
|
||||||
|
|
||||||
|
Set<String> ids = ZoneId.getAvailableZoneIds();
|
||||||
|
List<Integer> rawOffsets = new ArrayList<Integer>();
|
||||||
|
Map<Integer, List<NamePair>> map = new HashMap<Integer, List<NamePair>>();
|
||||||
|
for(String id : ids) {
|
||||||
|
if (id.startsWith("Etc/") || id.startsWith("SystemV/") || id.indexOf("/") < 0)
|
||||||
|
continue;
|
||||||
|
TimeZone tz = TimeZone.getTimeZone(ZoneId.of(id));
|
||||||
|
String label = getLabel(tz);
|
||||||
|
int rawOffset = tz.getRawOffset();
|
||||||
|
if (!rawOffsets.contains(rawOffset))
|
||||||
|
rawOffsets.add(rawOffset);
|
||||||
|
List<NamePair> timezones = map.get(rawOffset);
|
||||||
|
if (timezones == null) {
|
||||||
|
timezones = new ArrayList<NamePair>();
|
||||||
|
map.put(rawOffset, timezones);
|
||||||
|
}
|
||||||
|
ValueNamePair valueNamePair = new ValueNamePair(id, label);
|
||||||
|
timezones.add(valueNamePair);
|
||||||
|
}
|
||||||
|
Collections.sort(rawOffsets);
|
||||||
|
for(int rawOffset : rawOffsets) {
|
||||||
|
List<NamePair> namePairs = map.get(rawOffset);
|
||||||
|
Collections.sort(namePairs);
|
||||||
|
for(NamePair namePair : namePairs) {
|
||||||
|
getComponent().appendItem(namePair.getName(), namePair.getID());
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
getComponent().addEventListener(Events.ON_BLUR, e -> onBlur());
|
||||||
|
}
|
||||||
|
|
||||||
|
private void onBlur() {
|
||||||
|
Comboitem item = getComponent().getSelectedItem();
|
||||||
|
if (item == null)
|
||||||
|
{
|
||||||
|
setValue(oldValue);
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
//on select not fire for empty label item
|
||||||
|
if (Util.isEmpty(item.getLabel(),true))
|
||||||
|
{
|
||||||
|
String newValue = getValue();
|
||||||
|
if (isValueChange(newValue)) {
|
||||||
|
try {
|
||||||
|
if (gridField != null)
|
||||||
|
gridField.setLookupEditorSettingValue(true);
|
||||||
|
ValueChangeEvent changeEvent = new ValueChangeEvent(this, this.getColumnName(), oldValue, newValue);
|
||||||
|
super.fireValueChange(changeEvent);
|
||||||
|
oldValue = newValue;
|
||||||
|
} finally {
|
||||||
|
if (gridField != null)
|
||||||
|
gridField.setLookupEditorSettingValue(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean isValueChange(String newValue) {
|
||||||
|
return (oldValue == null && newValue != null) || (oldValue != null && newValue == null)
|
||||||
|
|| ((oldValue != null && newValue != null) && !oldValue.equals(newValue));
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.zkoss.zk.ui.event.EventListener#onEvent(org.zkoss.zk.ui.event.Event)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void onEvent(Event event) throws Exception {
|
||||||
|
if (Events.ON_CHANGE.equalsIgnoreCase(event.getName())) {
|
||||||
|
String id = getComponent().getSelectedItem() != null ? (String)getComponent().getSelectedItem().getValue() : (String)null;
|
||||||
|
String newValue = null;
|
||||||
|
|
||||||
|
if (id != null) {
|
||||||
|
newValue = id;
|
||||||
|
} else if (!Util.isEmpty(getComponent().getText(), true)) {
|
||||||
|
String customId = getComponent().getText();
|
||||||
|
if (processCustomZoneId(customId))
|
||||||
|
newValue = customId;
|
||||||
|
}
|
||||||
|
|
||||||
|
if (oldValue != null && newValue != null && oldValue.equals(newValue)) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
if (oldValue == null && newValue == null) {
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
ValueChangeEvent changeEvent = new ValueChangeEvent(this, this.getColumnName(), oldValue, newValue);
|
||||||
|
super.fireValueChange(changeEvent);
|
||||||
|
oldValue = newValue;
|
||||||
|
} else if (Events.ON_OPEN.equals(event.getName())) {
|
||||||
|
addTimeZoneMenu(popupMenu);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private boolean processCustomZoneId(String customId) {
|
||||||
|
TimeZone timeZone = TimeZone.getTimeZone(customId);
|
||||||
|
if (timeZone != null && timeZone.getID().equals(customId)) {
|
||||||
|
getComponent().appendItem(customId, customId);
|
||||||
|
getComponent().setSelectedIndex(getComponent().getItemCount()-1);
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#setReadWrite(boolean)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void setReadWrite(boolean readWrite) {
|
||||||
|
getComponent().setReadonly(!readWrite);
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#isReadWrite()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public boolean isReadWrite() {
|
||||||
|
return !getComponent().isReadonly();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#setValue(java.lang.Object)
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public void setValue(Object value) {
|
||||||
|
if (value == null || value.toString().trim().length() == 0) {
|
||||||
|
oldValue = null;
|
||||||
|
getComponent().setValue((Object)null);
|
||||||
|
getComponent().setSelectedItem(null);
|
||||||
|
getComponent().setText("");
|
||||||
|
} else if (value instanceof TimeZone) {
|
||||||
|
TimeZone tz = (TimeZone)value;
|
||||||
|
getComponent().setValue((Object)tz.getID());
|
||||||
|
oldValue = tz.getID();
|
||||||
|
} else {
|
||||||
|
getComponent().setValue(value);
|
||||||
|
if (getComponent().getSelectedItem() != null) {
|
||||||
|
oldValue = getComponent().getSelectedItem().getValue();
|
||||||
|
} else {
|
||||||
|
if (processCustomZoneId(value.toString()))
|
||||||
|
oldValue = getComponent().getSelectedItem().getValue();
|
||||||
|
else
|
||||||
|
oldValue = null;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#getValue()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String getValue() {
|
||||||
|
return getComponent().getValue();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#getDisplay()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public String getDisplay() {
|
||||||
|
return getComponent().getName();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getDisplayTextForGridView(Object value) {
|
||||||
|
if (value == null)
|
||||||
|
return "";
|
||||||
|
if (value instanceof TimeZone) {
|
||||||
|
return getLabel((TimeZone) value);
|
||||||
|
} else if (value instanceof String) {
|
||||||
|
String id = (String) value;
|
||||||
|
if (Util.isEmpty(id, true))
|
||||||
|
return (String) value;
|
||||||
|
TimeZone tz = TimeZone.getTimeZone((String) value);
|
||||||
|
if (tz != null && tz.getID().equals((String)value))
|
||||||
|
return getLabel(tz);
|
||||||
|
else
|
||||||
|
return (String) value;
|
||||||
|
}
|
||||||
|
return value.toString();
|
||||||
|
}
|
||||||
|
|
||||||
|
/* (non-Javadoc)
|
||||||
|
* @see org.adempiere.webui.editor.WEditor#getComponent()
|
||||||
|
*/
|
||||||
|
@Override
|
||||||
|
public Combobox getComponent() {
|
||||||
|
return (Combobox) super.getComponent();
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public void onMenu(ContextMenuEvent evt) {
|
||||||
|
if (TIME_ZONE.equals(evt.getContextEvent())) {
|
||||||
|
if (isReadWrite()) {
|
||||||
|
Component target = evt.getTarget();
|
||||||
|
if (target != null && target.getAttribute(TIME_ZONE_ID_ATTR) != null) {
|
||||||
|
String id = (String) target.getAttribute(TIME_ZONE_ID_ATTR);
|
||||||
|
setTimeZoneFromContextMenu(id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (WEditorPopupMenu.PREFERENCE_EVENT.equals(evt.getContextEvent()) && gridField != null) {
|
||||||
|
if (isShowPreference())
|
||||||
|
ValuePreference.start (getComponent(), this.getGridField(), getValue());
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
private void setTimeZoneFromContextMenu(String id) {
|
||||||
|
String newValue = id;
|
||||||
|
String currentValue = oldValue;
|
||||||
|
setValue(id);
|
||||||
|
if (getComponent().getSelectedItem() == null) {
|
||||||
|
newValue = null;
|
||||||
|
}
|
||||||
|
if (newValue != null) {
|
||||||
|
ValueChangeEvent changeEvent = new ValueChangeEvent(this, this.getColumnName(), currentValue, newValue);
|
||||||
|
super.fireValueChange(changeEvent);
|
||||||
|
oldValue = newValue;
|
||||||
|
} else if (currentValue != null) {
|
||||||
|
setValue(currentValue);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String[] getEvents() {
|
||||||
|
return LISTENER_EVENTS;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @param popupMenu
|
||||||
|
*/
|
||||||
|
private void addTimeZoneMenu(WEditorPopupMenu popupMenu) {
|
||||||
|
if (popupMenu != null && isReadWrite() && popupMenu.getAttribute(TIME_ZONE_ADDED) == null) {
|
||||||
|
ClientInfo clientInfo = SessionManager.getAppDesktop().getClientInfo();
|
||||||
|
if (clientInfo != null && clientInfo.timeZone != null) {
|
||||||
|
TimeZone firstSameRule = null;
|
||||||
|
TimeZone found = null;
|
||||||
|
for(int i = 0; i < getComponent().getItemCount(); i++) {
|
||||||
|
String id = getComponent().getItemAtIndex(i).getValue();
|
||||||
|
TimeZone tz = TimeZone.getTimeZone(id);
|
||||||
|
if (tz.getID().equals(clientInfo.timeZone.getID())) {
|
||||||
|
found = tz;
|
||||||
|
break;
|
||||||
|
} else if (tz.getRawOffset() == clientInfo.timeZone.getRawOffset() &&
|
||||||
|
tz.getDSTSavings() == clientInfo.timeZone.getDSTSavings() &&
|
||||||
|
tz.useDaylightTime() == clientInfo.timeZone.useDaylightTime()) {
|
||||||
|
if (firstSameRule == null)
|
||||||
|
firstSameRule = tz;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
TimeZone tz = found != null ? found : firstSameRule;
|
||||||
|
if (tz != null) {
|
||||||
|
Menuitem item = new Menuitem();
|
||||||
|
item.setLabel(getLabel(clientInfo.timeZone));
|
||||||
|
item.addEventListener(Events.ON_CLICK, popupMenu);
|
||||||
|
item.setAttribute(WEditorPopupMenu.EVENT_ATTRIBUTE, TIME_ZONE);
|
||||||
|
item.setAttribute(TIME_ZONE_ID_ATTR, tz.getID());
|
||||||
|
item.setAttribute(TIME_ZONE_ITEM_ATTR, Boolean.TRUE);
|
||||||
|
popupMenu.appendChild(item);
|
||||||
|
popupMenu.setAttribute(TIME_ZONE_ADDED, Boolean.TRUE);
|
||||||
|
}
|
||||||
|
|
||||||
|
if (popupMenu.getAttribute(TIME_ZONE_ADDED) == null) {
|
||||||
|
List<String> labels = new ArrayList<String>();
|
||||||
|
List<String> ids = new ArrayList<String>();
|
||||||
|
for(int i = 0; i < getComponent().getItemCount(); i++) {
|
||||||
|
String id = getComponent().getItemAtIndex(i).getValue();
|
||||||
|
tz = TimeZone.getTimeZone(id);
|
||||||
|
if (tz.getRawOffset() == clientInfo.timeZone.getRawOffset()) {
|
||||||
|
labels.add(getLabel(tz));
|
||||||
|
ids.add(id);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
if (labels.size() == 1) {
|
||||||
|
Menuitem item = new Menuitem();
|
||||||
|
item.setLabel(labels.get(0));
|
||||||
|
item.addEventListener(Events.ON_CLICK, popupMenu);
|
||||||
|
item.setAttribute(WEditorPopupMenu.EVENT_ATTRIBUTE, TIME_ZONE);
|
||||||
|
item.setAttribute(TIME_ZONE_ID_ATTR, ids.get(0));
|
||||||
|
item.setAttribute(TIME_ZONE_ITEM_ATTR, Boolean.TRUE);
|
||||||
|
popupMenu.appendChild(item);
|
||||||
|
} else {
|
||||||
|
Menu menu = new Menu();
|
||||||
|
menu.setLabel(Msg.getElement(Env.getCtx(), "TimeZone"));
|
||||||
|
menu.setAttribute(TIME_ZONE_ITEM_ATTR, Boolean.TRUE);
|
||||||
|
popupMenu.appendChild(menu);
|
||||||
|
Menupopup subPopup = new Menupopup();
|
||||||
|
menu.appendChild(subPopup);
|
||||||
|
for(int i = 0; i < labels.size(); i++) {
|
||||||
|
String label = labels.get(i);
|
||||||
|
String id = ids.get(i);
|
||||||
|
Menuitem item = new Menuitem();
|
||||||
|
item.setLabel(label);
|
||||||
|
item.addEventListener(Events.ON_CLICK, popupMenu);
|
||||||
|
item.setAttribute(WEditorPopupMenu.EVENT_ATTRIBUTE, TIME_ZONE);
|
||||||
|
item.setAttribute(TIME_ZONE_ID_ATTR, id);
|
||||||
|
subPopup.appendChild(item);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
popupMenu.setAttribute(TIME_ZONE_ADDED, Boolean.TRUE);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
} else if (popupMenu != null) {
|
||||||
|
List<Component> childs = popupMenu.getChildren();
|
||||||
|
for(Component c : childs) {
|
||||||
|
if (c.getAttribute(TIME_ZONE_ITEM_ATTR) != null) {
|
||||||
|
if (isReadWrite()) {
|
||||||
|
if (!c.isVisible())
|
||||||
|
c.setVisible(true);
|
||||||
|
} else {
|
||||||
|
if (c.isVisible())
|
||||||
|
c.setVisible(false);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param tz
|
||||||
|
* @return UTC offset + time zone id
|
||||||
|
*/
|
||||||
|
private String getLabel(TimeZone tz) {
|
||||||
|
String name = tz.getID();
|
||||||
|
int rawOffset = tz.getRawOffset();
|
||||||
|
int offsetMinutes = rawOffset / (60 * 1000);
|
||||||
|
boolean negative = false;
|
||||||
|
|
||||||
|
if (offsetMinutes < 0) {
|
||||||
|
negative = true;
|
||||||
|
offsetMinutes = -offsetMinutes;
|
||||||
|
}
|
||||||
|
|
||||||
|
final int h = offsetMinutes / 60;
|
||||||
|
final int m = offsetMinutes - h * 60;
|
||||||
|
|
||||||
|
StringBuilder fullName = new StringBuilder("UTC")
|
||||||
|
.append(((negative) ? "-" : "+"))
|
||||||
|
.append(((h < 10) ? "0" : "")).append(h).append(":")
|
||||||
|
.append(((m < 10) ? "0" : "")).append(m).append(" ")
|
||||||
|
.append(name);
|
||||||
|
return fullName.toString();
|
||||||
|
}
|
||||||
|
}
|
|
@ -17,6 +17,8 @@
|
||||||
|
|
||||||
package org.adempiere.webui.event;
|
package org.adempiere.webui.event;
|
||||||
|
|
||||||
|
import org.zkoss.zk.ui.Component;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @author <a href="mailto:agramdass@gmail.com">Ashley G Ramdass</a>
|
* @author <a href="mailto:agramdass@gmail.com">Ashley G Ramdass</a>
|
||||||
|
@ -26,14 +28,39 @@ package org.adempiere.webui.event;
|
||||||
public class ContextMenuEvent
|
public class ContextMenuEvent
|
||||||
{
|
{
|
||||||
private String contextEvent;
|
private String contextEvent;
|
||||||
|
private Component target;
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param event
|
||||||
|
*/
|
||||||
public ContextMenuEvent(String event)
|
public ContextMenuEvent(String event)
|
||||||
{
|
{
|
||||||
this.contextEvent = event;
|
this.contextEvent = event;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @return event name
|
||||||
|
*/
|
||||||
public String getContextEvent()
|
public String getContextEvent()
|
||||||
{
|
{
|
||||||
return contextEvent;
|
return contextEvent;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @param target
|
||||||
|
*/
|
||||||
|
public void setTarget(Component target) {
|
||||||
|
this.target = target;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @return target component
|
||||||
|
*/
|
||||||
|
public Component getTarget() {
|
||||||
|
return this.target;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
|
@ -41,6 +41,7 @@ import org.adempiere.webui.editor.WSearchEditor;
|
||||||
import org.adempiere.webui.editor.WStringEditor;
|
import org.adempiere.webui.editor.WStringEditor;
|
||||||
import org.adempiere.webui.editor.WTableDirEditor;
|
import org.adempiere.webui.editor.WTableDirEditor;
|
||||||
import org.adempiere.webui.editor.WTimeEditor;
|
import org.adempiere.webui.editor.WTimeEditor;
|
||||||
|
import org.adempiere.webui.editor.WTimeZoneEditor;
|
||||||
import org.adempiere.webui.editor.WUnknownEditor;
|
import org.adempiere.webui.editor.WUnknownEditor;
|
||||||
import org.adempiere.webui.editor.WUrlEditor;
|
import org.adempiere.webui.editor.WUrlEditor;
|
||||||
import org.adempiere.webui.editor.WYesNoEditor;
|
import org.adempiere.webui.editor.WYesNoEditor;
|
||||||
|
@ -131,7 +132,7 @@ public class DefaultEditorFactory implements IEditorFactory {
|
||||||
{
|
{
|
||||||
if (displayType == DisplayType.Time)
|
if (displayType == DisplayType.Time)
|
||||||
editor = new WTimeEditor(gridField, tableEditor, editorConfiguration);
|
editor = new WTimeEditor(gridField, tableEditor, editorConfiguration);
|
||||||
else if (displayType == DisplayType.DateTime)
|
else if (displayType == DisplayType.DateTime || displayType == DisplayType.TimestampWithTimeZone)
|
||||||
editor = new WDatetimeEditor(gridField, tableEditor, editorConfiguration);
|
editor = new WDatetimeEditor(gridField, tableEditor, editorConfiguration);
|
||||||
else
|
else
|
||||||
editor = new WDateEditor(gridField, tableEditor, editorConfiguration);
|
editor = new WDateEditor(gridField, tableEditor, editorConfiguration);
|
||||||
|
@ -225,6 +226,10 @@ public class DefaultEditorFactory implements IEditorFactory {
|
||||||
{
|
{
|
||||||
editor = new WRadioGroupEditor(gridField, tableEditor, editorConfiguration);
|
editor = new WRadioGroupEditor(gridField, tableEditor, editorConfiguration);
|
||||||
}
|
}
|
||||||
|
else if (displayType == DisplayType.TimeZoneId)
|
||||||
|
{
|
||||||
|
editor = new WTimeZoneEditor(gridField, tableEditor);
|
||||||
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
editor = new WUnknownEditor(gridField, tableEditor, editorConfiguration);
|
editor = new WUnknownEditor(gridField, tableEditor, editorConfiguration);
|
||||||
|
|
|
@ -1406,6 +1406,11 @@ public class DB_Oracle implements AdempiereDatabase
|
||||||
return "DATE";
|
return "DATE";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getTimestampWithTimezoneDataType() {
|
||||||
|
return "TIMESTAMP WITH TIME ZONE";
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getSQLDDL(MColumn column) {
|
public String getSQLDDL(MColumn column) {
|
||||||
StringBuilder sql = new StringBuilder ().append(column.getColumnName())
|
StringBuilder sql = new StringBuilder ().append(column.getColumnName())
|
||||||
|
|
|
@ -1296,6 +1296,11 @@ public class DB_PostgreSQL implements AdempiereDatabase
|
||||||
return "TIMESTAMP";
|
return "TIMESTAMP";
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
public String getTimestampWithTimezoneDataType() {
|
||||||
|
return "TIMESTAMP WITH TIME ZONE";
|
||||||
|
}
|
||||||
|
|
||||||
@Override
|
@Override
|
||||||
public String getSQLDDL(MColumn column) {
|
public String getSQLDDL(MColumn column) {
|
||||||
StringBuilder sql = new StringBuilder ().append(column.getColumnName())
|
StringBuilder sql = new StringBuilder ().append(column.getColumnName())
|
||||||
|
|
|
@ -0,0 +1,153 @@
|
||||||
|
/***********************************************************************
|
||||||
|
* This file is part of iDempiere ERP Open Source *
|
||||||
|
* http://www.idempiere.org *
|
||||||
|
* *
|
||||||
|
* Copyright (C) Contributors *
|
||||||
|
* *
|
||||||
|
* This program is free software; you can redistribute it and/or *
|
||||||
|
* modify it under the terms of the GNU General Public License *
|
||||||
|
* as published by the Free Software Foundation; either version 2 *
|
||||||
|
* of the License, or (at your option) any later version. *
|
||||||
|
* *
|
||||||
|
* This program is distributed in the hope that it will be useful, *
|
||||||
|
* but WITHOUT ANY WARRANTY; without even the implied warranty of *
|
||||||
|
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the *
|
||||||
|
* GNU General Public License for more details. *
|
||||||
|
* *
|
||||||
|
* You should have received a copy of the GNU General Public License *
|
||||||
|
* along with this program; if not, write to the Free Software *
|
||||||
|
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, *
|
||||||
|
* MA 02110-1301, USA. *
|
||||||
|
* *
|
||||||
|
* Contributors: *
|
||||||
|
* - hengsin *
|
||||||
|
**********************************************************************/
|
||||||
|
package org.idempiere.test.model;
|
||||||
|
|
||||||
|
import static org.junit.jupiter.api.Assertions.assertEquals;
|
||||||
|
import static org.junit.jupiter.api.Assertions.assertFalse;
|
||||||
|
|
||||||
|
import java.sql.Timestamp;
|
||||||
|
import java.time.format.DateTimeFormatter;
|
||||||
|
import java.util.Calendar;
|
||||||
|
import java.util.TimeZone;
|
||||||
|
|
||||||
|
import org.compiere.model.MClientInfo;
|
||||||
|
import org.compiere.model.MSchedule;
|
||||||
|
import org.compiere.model.MScheduler;
|
||||||
|
import org.compiere.model.PO;
|
||||||
|
import org.compiere.util.CacheMgt;
|
||||||
|
import org.compiere.util.Env;
|
||||||
|
import org.compiere.util.Util;
|
||||||
|
import org.idempiere.test.AbstractTestCase;
|
||||||
|
import org.junit.jupiter.api.Test;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* @author hengsin
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public class MSchedulerTest extends AbstractTestCase {
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
public MSchedulerTest() {
|
||||||
|
}
|
||||||
|
|
||||||
|
@Test
|
||||||
|
public void testCronSchedulingPatternWithTimeZone() {
|
||||||
|
MSchedule schedule = null;
|
||||||
|
MClientInfo clientInfo = MClientInfo.getCopy(Env.getCtx(), getAD_Client_ID(), null);
|
||||||
|
String currentTimeZone = clientInfo.getTimeZone();
|
||||||
|
try {
|
||||||
|
schedule = new MSchedule(Env.getCtx(), 0, null);
|
||||||
|
schedule.setName("Every Day at 5 pm Test");
|
||||||
|
schedule.setScheduleType(MSchedule.SCHEDULETYPE_CronSchedulingPattern);
|
||||||
|
schedule.setIsSystemSchedule(false);
|
||||||
|
schedule.setCronPattern("0 17 * * *");
|
||||||
|
try {
|
||||||
|
PO.setCrossTenantSafe();
|
||||||
|
schedule.saveEx();
|
||||||
|
} finally {
|
||||||
|
PO.clearCrossTenantSafe();
|
||||||
|
}
|
||||||
|
|
||||||
|
//get jvm timezone
|
||||||
|
//this test assume jvm and db server is using the same default time zone
|
||||||
|
TimeZone tz1 = TimeZone.getDefault();
|
||||||
|
Calendar cal1 = Calendar.getInstance();
|
||||||
|
cal1.setTimeZone(tz1);
|
||||||
|
cal1.setTimeInMillis(System.currentTimeMillis());
|
||||||
|
int hour = cal1.get(Calendar.HOUR_OF_DAY);
|
||||||
|
if (hour > 17) {
|
||||||
|
cal1.add(Calendar.DAY_OF_MONTH, 1);
|
||||||
|
}
|
||||||
|
cal1.set(Calendar.HOUR_OF_DAY, 17);
|
||||||
|
cal1.set(Calendar.MINUTE, 0);
|
||||||
|
cal1.set(Calendar.SECOND, 0);
|
||||||
|
cal1.set(Calendar.MILLISECOND, 0);
|
||||||
|
|
||||||
|
//get timezone with +2 hour offset
|
||||||
|
String[] ids = TimeZone.getAvailableIDs(tz1.getRawOffset()+(2*60*60*1000));
|
||||||
|
TimeZone tz2 = TimeZone.getTimeZone(ids[0]);
|
||||||
|
Calendar cal2 = Calendar.getInstance();
|
||||||
|
cal2.setTimeZone(tz2);
|
||||||
|
cal2.setTimeInMillis(System.currentTimeMillis());
|
||||||
|
hour = cal2.get(Calendar.HOUR_OF_DAY);
|
||||||
|
if (hour > 17) {
|
||||||
|
cal2.add(Calendar.DAY_OF_MONTH, 1);
|
||||||
|
}
|
||||||
|
cal2.set(Calendar.HOUR_OF_DAY, 17);
|
||||||
|
cal2.set(Calendar.MINUTE, 0);
|
||||||
|
cal2.set(Calendar.SECOND, 0);
|
||||||
|
cal2.set(Calendar.MILLISECOND, 0);
|
||||||
|
|
||||||
|
//formatter for comparison
|
||||||
|
DateTimeFormatter formatter1 = DateTimeFormatter.ISO_ZONED_DATE_TIME;
|
||||||
|
formatter1 = formatter1.withZone(tz1.toZoneId());
|
||||||
|
DateTimeFormatter formatter2 = DateTimeFormatter.ISO_ZONED_DATE_TIME;
|
||||||
|
formatter2 = formatter2.withZone(tz2.toZoneId());
|
||||||
|
|
||||||
|
//test with default time zone
|
||||||
|
if (!Util.isEmpty(currentTimeZone, true)) {
|
||||||
|
clientInfo.setTimeZone(null);
|
||||||
|
clientInfo.saveEx();
|
||||||
|
CacheMgt.get().reset();
|
||||||
|
}
|
||||||
|
MScheduler scheduler1 = new MScheduler(Env.getCtx(), 0, getTrxName());
|
||||||
|
scheduler1.setAD_Process_ID(121); //Open Orders Process Id
|
||||||
|
scheduler1.setAD_Schedule_ID(schedule.get_ID());
|
||||||
|
scheduler1.setName("Cron Scheduler Test 1");
|
||||||
|
scheduler1.setSupervisor_ID(100);
|
||||||
|
scheduler1.saveEx();
|
||||||
|
|
||||||
|
Timestamp ts1 = scheduler1.getDateNextRun();
|
||||||
|
assertEquals(formatter1.format(cal1.getTime().toInstant()), formatter1.format(ts1.toInstant()), "Un-expected date next run");
|
||||||
|
assertFalse(cal2.getTimeInMillis() == ts1.getTime(), "Un-expected date next run");
|
||||||
|
|
||||||
|
//test with default + 2hour time zone
|
||||||
|
clientInfo.setTimeZone(tz2.getID());
|
||||||
|
clientInfo.saveEx();
|
||||||
|
CacheMgt.get().reset();
|
||||||
|
|
||||||
|
MScheduler scheduler2 = new MScheduler(Env.getCtx(), 0, getTrxName());
|
||||||
|
scheduler2.setAD_Process_ID(121);
|
||||||
|
scheduler2.setAD_Schedule_ID(schedule.get_ID());
|
||||||
|
scheduler2.setName("Cron Scheduler Test 2");
|
||||||
|
scheduler2.setSupervisor_ID(100);
|
||||||
|
scheduler2.saveEx();
|
||||||
|
|
||||||
|
Timestamp ts2 = scheduler2.getDateNextRun();
|
||||||
|
assertEquals(formatter2.format(cal2.getTime().toInstant()), formatter2.format(ts2.toInstant()), "Un-expected date next run");
|
||||||
|
assertFalse(cal1.getTimeInMillis() == ts2.getTime(), "Un-expected date next run");
|
||||||
|
} finally {
|
||||||
|
if (schedule != null && schedule.get_ID() > 0)
|
||||||
|
schedule.deleteEx(true);
|
||||||
|
if (!Util.isEmpty(currentTimeZone, true)) {
|
||||||
|
clientInfo.setTimeZone(currentTimeZone);
|
||||||
|
clientInfo.saveEx();
|
||||||
|
CacheMgt.get().reset();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
Loading…
Reference in New Issue