Fix database cache expunge issues (#1489149) - added 'expires' column
4 files added
12 files modified
| | |
| | | CHANGELOG Roundcube Webmail |
| | | =========================== |
| | | |
| | | - Fix database cache expunge issues (#1489149) |
| | | - Fix date format issues on MS SQL Server (#1488918) |
| | | - Fix so non-inline images aren't skipped on forward (#1489150) |
| | | - Add imap_cache_ttl option to configure TTL of imap_cache |
| | |
| | | [user_id] [int] NOT NULL ,
|
| | | [cache_key] [varchar] (128) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [created] [datetime] NOT NULL ,
|
| | | [expires] [datetime] NULL ,
|
| | | [data] [text] COLLATE Latin1_General_CI_AI NOT NULL
|
| | | ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
| | | GO
|
| | |
| | | CREATE TABLE [dbo].[cache_shared] (
|
| | | [cache_key] [varchar] (255) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [created] [datetime] NOT NULL ,
|
| | | [expires] [datetime] NULL ,
|
| | | [data] [text] COLLATE Latin1_General_CI_AI NOT NULL
|
| | | ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
| | | GO
|
| | |
| | | CREATE TABLE [dbo].[cache_index] (
|
| | | [user_id] [int] NOT NULL ,
|
| | | [mailbox] [varchar] (128) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [changed] [datetime] NOT NULL ,
|
| | | [expires] [datetime] NULL ,
|
| | | [valid] [char] (1) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [data] [text] COLLATE Latin1_General_CI_AI NOT NULL
|
| | | ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
| | |
| | | CREATE TABLE [dbo].[cache_thread] (
|
| | | [user_id] [int] NOT NULL ,
|
| | | [mailbox] [varchar] (128) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [changed] [datetime] NOT NULL ,
|
| | | [expires] [datetime] NULL ,
|
| | | [data] [text] COLLATE Latin1_General_CI_AI NOT NULL
|
| | | ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
| | | GO
|
| | |
| | | [user_id] [int] NOT NULL ,
|
| | | [mailbox] [varchar] (128) COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [uid] [int] NOT NULL ,
|
| | | [changed] [datetime] NOT NULL ,
|
| | | [expires] [datetime] NULL ,
|
| | | [data] [text] COLLATE Latin1_General_CI_AI NOT NULL ,
|
| | | [flags] [int] NOT NULL
|
| | | ) ON [PRIMARY] TEXTIMAGE_ON [PRIMARY]
|
| | |
| | | CONSTRAINT [DF_cache_created] DEFAULT (getdate()) FOR [created]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_shared] ADD |
| | | CONSTRAINT [DF_cache_shared_created] DEFAULT (getdate()) FOR [created]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_index] ADD |
| | | CONSTRAINT [DF_cache_index_valid] DEFAULT ('0') FOR [valid]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_messages] ADD |
| | | CONSTRAINT [DF_cache_messages_flags] DEFAULT (0) FOR [flags]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_user_id] ON [dbo].[cache]([user_id]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_cache_key] ON [dbo].[cache]([cache_key]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_created] ON [dbo].[cache]([created]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_shared] ADD |
| | | CONSTRAINT [DF_cache_shared_created] DEFAULT (getdate()) FOR [created]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_shared_cache_key] ON [dbo].[cache_shared]([cache_key]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_shared_created] ON [dbo].[cache_shared]([created]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_index] ADD |
| | | CONSTRAINT [DF_cache_index_changed] DEFAULT (getdate()) FOR [changed],
|
| | | CONSTRAINT [DF_cache_index_valid] DEFAULT ('0') FOR [valid]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_index_user_id] ON [dbo].[cache_index]([user_id]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_thread] ADD |
| | | CONSTRAINT [DF_cache_thread_changed] DEFAULT (getdate()) FOR [changed]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_thread_user_id] ON [dbo].[cache_thread]([user_id]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[cache_messages] ADD |
| | | CONSTRAINT [DF_cache_messages_changed] DEFAULT (getdate()) FOR [changed],
|
| | | CONSTRAINT [DF_cache_messages_flags] DEFAULT (0) FOR [flags]
|
| | | CREATE INDEX [IX_cache_messages_user_id] ON [dbo].[cache_messages]([user_id]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_messages_user_id] ON [dbo].[cache_messages]([user_id]) ON [PRIMARY]
|
| | | CREATE INDEX [IX_cache_expires] ON [dbo].[cache]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_shared_expires] ON [dbo].[cache_shared]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_index_expires] ON [dbo].[cache_index]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_thread_expires] ON [dbo].[cache_thread]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_messages_expires] ON [dbo].[cache_messages]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | | ALTER TABLE [dbo].[contacts] ADD
|
| | |
| | | WHERE [contact_id] IN (SELECT [contact_id] FROM deleted)
|
| | | GO
|
| | |
|
| | | INSERT INTO [dbo].[system] ([name], [value]) VALUES ('roundcube-version', '2013052500')
|
| | | INSERT INTO [dbo].[system] ([name], [value]) VALUES ('roundcube-version', '2013061000')
|
| | | GO
|
| | |
|
New file |
| | |
| | | ALTER TABLE [dbo].[cache] ADD COLUMN [expires] [datetime] NULL
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_shared] ADD COLUMN [expires] [datetime] NULL
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_index] ADD COLUMN [expires] [datetime] NULL
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_thread] ADD COLUMN [expires] [datetime] NULL
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_messages] ADD COLUMN [expires] [datetime] NULL
|
| | | GO
|
| | |
|
| | | UPDATE [dbo].[cache] SET [expires] = DATEADD(second, 604800, [created])
|
| | | GO
|
| | | UPDATE [dbo].[cache_shared] SET [expires] = DATEADD(second, 604800, [created])
|
| | | GO
|
| | | UPDATE [dbo].[cache_index] SET [expires] = DATEADD(second, 604800, [changed])
|
| | | GO
|
| | | UPDATE [dbo].[cache_thread] SET [expires] = DATEADD(second, 604800, [changed])
|
| | | GO
|
| | | UPDATE [dbo].[cache_messages] SET [expires] = DATEADD(second, 604800, [changed])
|
| | | GO
|
| | |
|
| | | DROP INDEX [IX_cache_created]
|
| | | GO
|
| | | DROP INDEX [IX_cache_shared_created]
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_index] DROP COLUMN [changed]
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_thread] DROP COLUMN [changed]
|
| | | GO
|
| | | ALTER TABLE [dbo].[cache_messages] DROP COLUMN [changed]
|
| | | GO
|
| | |
|
| | | CREATE INDEX [IX_cache_expires] ON [dbo].[cache]([expires]) ON [PRIMARY]
|
| | | GO
|
| | | CREATE INDEX [IX_cache_shared_expires] ON [dbo].[cache_shared]([expires]) ON [PRIMARY]
|
| | | GO
|
| | | CREATE INDEX [IX_cache_index_expires] ON [dbo].[cache_index]([expires]) ON [PRIMARY]
|
| | | GO
|
| | | CREATE INDEX [IX_cache_thread_expires] ON [dbo].[cache_thread]([expires]) ON [PRIMARY]
|
| | | GO
|
| | | CREATE INDEX [IX_cache_messages_expires] ON [dbo].[cache_messages]([expires]) ON [PRIMARY]
|
| | | GO
|
| | |
|
| | |
| | | `user_id` int(10) UNSIGNED NOT NULL, |
| | | `cache_key` varchar(128) /*!40101 CHARACTER SET ascii COLLATE ascii_general_ci */ NOT NULL , |
| | | `created` datetime NOT NULL DEFAULT '1000-01-01 00:00:00', |
| | | `expires` datetime DEFAULT NULL, |
| | | `data` longtext NOT NULL, |
| | | CONSTRAINT `user_id_fk_cache` FOREIGN KEY (`user_id`) |
| | | REFERENCES `users`(`user_id`) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | INDEX `created_index` (`created`), |
| | | INDEX `expires_index` (`expires`), |
| | | INDEX `user_cache_index` (`user_id`,`cache_key`) |
| | | ) /*!40000 ENGINE=INNODB */ /*!40101 CHARACTER SET utf8 COLLATE utf8_general_ci */; |
| | | |
| | |
| | | CREATE TABLE `cache_shared` ( |
| | | `cache_key` varchar(255) /*!40101 CHARACTER SET ascii COLLATE ascii_general_ci */ NOT NULL , |
| | | `created` datetime NOT NULL DEFAULT '1000-01-01 00:00:00', |
| | | `expires` datetime DEFAULT NULL, |
| | | `data` longtext NOT NULL, |
| | | INDEX `created_index` (`created`), |
| | | INDEX `expires_index` (`expires`), |
| | | INDEX `cache_key_index` (`cache_key`) |
| | | ) /*!40000 ENGINE=INNODB */ /*!40101 CHARACTER SET utf8 COLLATE utf8_general_ci */; |
| | | |
| | |
| | | CREATE TABLE `cache_index` ( |
| | | `user_id` int(10) UNSIGNED NOT NULL, |
| | | `mailbox` varchar(255) BINARY NOT NULL, |
| | | `changed` datetime NOT NULL DEFAULT '1000-01-01 00:00:00', |
| | | `expires` datetime DEFAULT NULL, |
| | | `valid` tinyint(1) NOT NULL DEFAULT '0', |
| | | `data` longtext NOT NULL, |
| | | CONSTRAINT `user_id_fk_cache_index` FOREIGN KEY (`user_id`) |
| | | REFERENCES `users`(`user_id`) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | INDEX `changed_index` (`changed`), |
| | | INDEX `expires_index` (`expires`), |
| | | PRIMARY KEY (`user_id`, `mailbox`) |
| | | ) /*!40000 ENGINE=INNODB */ /*!40101 CHARACTER SET utf8 COLLATE utf8_general_ci */; |
| | | |
| | |
| | | CREATE TABLE `cache_thread` ( |
| | | `user_id` int(10) UNSIGNED NOT NULL, |
| | | `mailbox` varchar(255) BINARY NOT NULL, |
| | | `changed` datetime NOT NULL DEFAULT '1000-01-01 00:00:00', |
| | | `expires` datetime DEFAULT NULL, |
| | | `data` longtext NOT NULL, |
| | | CONSTRAINT `user_id_fk_cache_thread` FOREIGN KEY (`user_id`) |
| | | REFERENCES `users`(`user_id`) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | INDEX `changed_index` (`changed`), |
| | | INDEX `expires_index` (`expires`), |
| | | PRIMARY KEY (`user_id`, `mailbox`) |
| | | ) /*!40000 ENGINE=INNODB */ /*!40101 CHARACTER SET utf8 COLLATE utf8_general_ci */; |
| | | |
| | |
| | | `user_id` int(10) UNSIGNED NOT NULL, |
| | | `mailbox` varchar(255) BINARY NOT NULL, |
| | | `uid` int(11) UNSIGNED NOT NULL DEFAULT '0', |
| | | `changed` datetime NOT NULL DEFAULT '1000-01-01 00:00:00', |
| | | `expires` datetime DEFAULT NULL, |
| | | `data` longtext NOT NULL, |
| | | `flags` int(11) NOT NULL DEFAULT '0', |
| | | CONSTRAINT `user_id_fk_cache_messages` FOREIGN KEY (`user_id`) |
| | | REFERENCES `users`(`user_id`) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | INDEX `changed_index` (`changed`), |
| | | INDEX `expires_index` (`expires`), |
| | | PRIMARY KEY (`user_id`, `mailbox`, `uid`) |
| | | ) /*!40000 ENGINE=INNODB */ /*!40101 CHARACTER SET utf8 COLLATE utf8_general_ci */; |
| | | |
| | |
| | | |
| | | /*!40014 SET FOREIGN_KEY_CHECKS=1 */; |
| | | |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013052500'); |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013061000'); |
New file |
| | |
| | | ALTER TABLE `cache` ADD `expires` datetime DEFAULT NULL; |
| | | ALTER TABLE `cache_shared` ADD `expires` datetime DEFAULT NULL; |
| | | ALTER TABLE `cache_index` ADD `expires` datetime DEFAULT NULL; |
| | | ALTER TABLE `cache_thread` ADD `expires` datetime DEFAULT NULL; |
| | | ALTER TABLE `cache_messages` ADD `expires` datetime DEFAULT NULL; |
| | | |
| | | -- initialize expires column with created/changed date + 7days |
| | | UPDATE `cache` SET `expires` = `created` + interval 604800 second; |
| | | UPDATE `cache_shared` SET `expires` = `created` + interval 604800 second; |
| | | UPDATE `cache_index` SET `expires` = `changed` + interval 604800 second; |
| | | UPDATE `cache_thread` SET `expires` = `changed` + interval 604800 second; |
| | | UPDATE `cache_messages` SET `expires` = `changed` + interval 604800 second; |
| | | |
| | | ALTER TABLE `cache` DROP INDEX `created_index`; |
| | | ALTER TABLE `cache_shared` DROP INDEX `created_index`; |
| | | ALTER TABLE `cache_index` DROP `changed`; |
| | | ALTER TABLE `cache_thread` DROP `changed`; |
| | | ALTER TABLE `cache_messages` DROP `changed`; |
| | | |
| | | ALTER TABLE `cache` ADD INDEX `expires_index` (`expires`); |
| | | ALTER TABLE `cache_shared` ADD INDEX `expires_index` (`expires`); |
| | | ALTER TABLE `cache_index` ADD INDEX `expires_index` (`expires`); |
| | | ALTER TABLE `cache_thread` ADD INDEX `expires_index` (`expires`); |
| | | ALTER TABLE `cache_messages` ADD INDEX `expires_index` (`expires`); |
| | |
| | | REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | cache_key varchar(128) DEFAULT '' NOT NULL, |
| | | created timestamp with time zone DEFAULT now() NOT NULL, |
| | | expires timestamp with time zone DEFAULT NULL, |
| | | data text NOT NULL |
| | | ); |
| | | |
| | | CREATE INDEX cache_user_id_idx ON "cache" (user_id, cache_key); |
| | | CREATE INDEX cache_created_idx ON "cache" (created); |
| | | CREATE INDEX cache_expires_idx ON "cache" (expires); |
| | | |
| | | -- |
| | | -- Table "cache_shared" |
| | |
| | | CREATE TABLE "cache_shared" ( |
| | | cache_key varchar(255) NOT NULL, |
| | | created timestamp with time zone DEFAULT now() NOT NULL, |
| | | expires timestamp with time zone DEFAULT NULL, |
| | | data text NOT NULL |
| | | ); |
| | | |
| | | CREATE INDEX cache_shared_cache_key_idx ON "cache_shared" (cache_key); |
| | | CREATE INDEX cache_shared_created_idx ON "cache_shared" (created); |
| | | CREATE INDEX cache_shared_expires_idx ON "cache_shared" (expires); |
| | | |
| | | -- |
| | | -- Table "cache_index" |
| | |
| | | user_id integer NOT NULL |
| | | REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | mailbox varchar(255) NOT NULL, |
| | | changed timestamp with time zone DEFAULT now() NOT NULL, |
| | | expires timestamp with time zone DEFAULT NULL, |
| | | valid smallint NOT NULL DEFAULT 0, |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX cache_index_changed_idx ON cache_index (changed); |
| | | CREATE INDEX cache_index_expires_idx ON cache_index (expires); |
| | | |
| | | -- |
| | | -- Table "cache_thread" |
| | |
| | | user_id integer NOT NULL |
| | | REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | mailbox varchar(255) NOT NULL, |
| | | changed timestamp with time zone DEFAULT now() NOT NULL, |
| | | expires timestamp with time zone DEFAULT NULL, |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX cache_thread_changed_idx ON cache_thread (changed); |
| | | CREATE INDEX cache_thread_expires_idx ON cache_thread (expires); |
| | | |
| | | -- |
| | | -- Table "cache_messages" |
| | |
| | | REFERENCES users (user_id) ON DELETE CASCADE ON UPDATE CASCADE, |
| | | mailbox varchar(255) NOT NULL, |
| | | uid integer NOT NULL, |
| | | changed timestamp with time zone DEFAULT now() NOT NULL, |
| | | expires timestamp with time zone DEFAULT NULL, |
| | | data text NOT NULL, |
| | | flags integer NOT NULL DEFAULT 0, |
| | | PRIMARY KEY (user_id, mailbox, uid) |
| | | ); |
| | | |
| | | CREATE INDEX cache_messages_changed_idx ON cache_messages (changed); |
| | | CREATE INDEX cache_messages_expires_idx ON cache_messages (expires); |
| | | |
| | | -- |
| | | -- Table "dictionary" |
| | |
| | | value text |
| | | ); |
| | | |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013052500'); |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013061000'); |
New file |
| | |
| | | ALTER TABLE "cache" ADD expires timestamp with time zone DEFAULT NULL; |
| | | ALTER TABLE "cache_shared" ADD expires timestamp with time zone DEFAULT NULL; |
| | | ALTER TABLE "cache_index" ADD expires timestamp with time zone DEFAULT NULL; |
| | | ALTER TABLE "cache_thread" ADD expires timestamp with time zone DEFAULT NULL; |
| | | ALTER TABLE "cache_messages" ADD expires timestamp with time zone DEFAULT NULL; |
| | | |
| | | -- initialize expires column with created/changed date + 7days |
| | | UPDATE "cache" SET expires = created + interval '604800 seconds'; |
| | | UPDATE "cache_shared" SET expires = created + interval '604800 seconds'; |
| | | UPDATE "cache_index" SET expires = changed + interval '604800 seconds'; |
| | | UPDATE "cache_thread" SET expires = changed + interval '604800 seconds'; |
| | | UPDATE "cache_messages" SET expires = changed + interval '604800 seconds'; |
| | | |
| | | DROP INDEX cache_created_idx; |
| | | DROP INDEX cache_shared_created_idx; |
| | | ALTER TABLE "cache_index" DROP "changed"; |
| | | ALTER TABLE "cache_thread" DROP "changed"; |
| | | ALTER TABLE "cache_messages" DROP "changed"; |
| | | |
| | | CREATE INDEX cache_expires_idx ON "cache" (expires); |
| | | CREATE INDEX cache_shared_expires_idx ON "cache_shared" (expires); |
| | | CREATE INDEX cache_index_expires_idx ON "cache_index" (expires); |
| | | CREATE INDEX cache_thread_expires_idx ON "cache_thread" (expires); |
| | | CREATE INDEX cache_messages_expires_idx ON "cache_messages" (expires); |
| | |
| | | user_id integer NOT NULL default 0, |
| | | cache_key varchar(128) NOT NULL default '', |
| | | created datetime NOT NULL default '0000-00-00 00:00:00', |
| | | expires datetime DEFAULT NOT, |
| | | data text NOT NULL |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_user_cache_key ON cache(user_id, cache_key); |
| | | CREATE INDEX ix_cache_created ON cache(created); |
| | | CREATE INDEX ix_cache_expires ON cache(expires); |
| | | |
| | | -- |
| | | -- Table structure for table cache_shared |
| | |
| | | CREATE TABLE cache_shared ( |
| | | cache_key varchar(255) NOT NULL, |
| | | created datetime NOT NULL default '0000-00-00 00:00:00', |
| | | expires datetime DEFAULT NULL, |
| | | data text NOT NULL |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_shared_cache_key ON cache_shared(cache_key); |
| | | CREATE INDEX ix_cache_shared_created ON cache_shared(created); |
| | | CREATE INDEX ix_cache_shared_expires ON cache_shared(expires); |
| | | |
| | | -- |
| | | -- Table structure for table cache_index |
| | |
| | | CREATE TABLE cache_index ( |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | changed datetime NOT NULL default '0000-00-00 00:00:00', |
| | | expires datetime DEFAULT NULL, |
| | | valid smallint NOT NULL DEFAULT '0', |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_index_changed ON cache_index (changed); |
| | | CREATE INDEX ix_cache_index_expires ON cache_index (expires); |
| | | |
| | | -- |
| | | -- Table structure for table cache_thread |
| | |
| | | CREATE TABLE cache_thread ( |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | changed datetime NOT NULL default '0000-00-00 00:00:00', |
| | | expires datetime DEFAULT NULL, |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_thread_changed ON cache_thread (changed); |
| | | CREATE INDEX ix_cache_thread_expires ON cache_thread (expires); |
| | | |
| | | -- |
| | | -- Table structure for table cache_messages |
| | |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | uid integer NOT NULL, |
| | | changed datetime NOT NULL default '0000-00-00 00:00:00', |
| | | expires datetime DEFAULT NULL, |
| | | data text NOT NULL, |
| | | flags integer NOT NULL DEFAULT '0', |
| | | PRIMARY KEY (user_id, mailbox, uid) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_messages_changed ON cache_messages (changed); |
| | | CREATE INDEX ix_cache_messages_expires ON cache_messages (expires); |
| | | |
| | | -- |
| | | -- Table structure for table system |
| | |
| | | value text NOT NULL |
| | | ); |
| | | |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013052500'); |
| | | INSERT INTO system (name, value) VALUES ('roundcube-version', '2013061000'); |
New file |
| | |
| | | DROP TABLE cache_index; |
| | | DROP TABLE cache_thread; |
| | | DROP TABLE cache_messages; |
| | | |
| | | ALTER TABLE cache ADD expires datetime DEFAULT NULL; |
| | | DROP INDEX ix_cache_created; |
| | | |
| | | ALTER TABLE cache_shared ADD expires datetime DEFAULT NULL; |
| | | DROP INDEX ix_cache_shared_created; |
| | | |
| | | UPDATE cache SET expires = datetime(created, '+604800 seconds'); |
| | | UPDATE cache_shared SET expires = datetime(created, '+604800 seconds'); |
| | | |
| | | CREATE INDEX ix_cache_expires ON cache(expires); |
| | | CREATE INDEX ix_cache_shared_expires ON cache_shared(expires); |
| | | |
| | | CREATE TABLE cache_index ( |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | expires datetime DEFAULT NULL, |
| | | valid smallint NOT NULL DEFAULT '0', |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_index_expires ON cache_index (expires); |
| | | |
| | | CREATE TABLE cache_thread ( |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | expires datetime DEFAULT NULL, |
| | | data text NOT NULL, |
| | | PRIMARY KEY (user_id, mailbox) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_thread_expires ON cache_thread (expires); |
| | | |
| | | CREATE TABLE cache_messages ( |
| | | user_id integer NOT NULL, |
| | | mailbox varchar(255) NOT NULL, |
| | | uid integer NOT NULL, |
| | | expires datetime DEFAULT NULL, |
| | | data text NOT NULL, |
| | | flags integer NOT NULL DEFAULT '0', |
| | | PRIMARY KEY (user_id, mailbox, uid) |
| | | ); |
| | | |
| | | CREATE INDEX ix_cache_messages_expires ON cache_messages (expires); |
| | |
| | | */ |
| | | public function gc() |
| | | { |
| | | foreach ($this->caches as $cache) { |
| | | if (is_object($cache)) { |
| | | $cache->expunge(); |
| | | } |
| | | } |
| | | |
| | | if (is_object($this->storage)) { |
| | | $this->storage->expunge_cache(); |
| | | } |
| | | rcube_cache::gc(); |
| | | rcube_cache_shared::gc(); |
| | | $this->get_storage()->cache_gc(); |
| | | |
| | | $this->gc_temp(); |
| | | } |
| | |
| | | private $type; |
| | | private $userid; |
| | | private $prefix; |
| | | private $table; |
| | | private $ttl; |
| | | private $packed; |
| | | private $index; |
| | |
| | | else { |
| | | $this->type = 'db'; |
| | | $this->db = $rcube->get_dbh(); |
| | | $this->table = $this->db->table_name('cache'); |
| | | } |
| | | |
| | | // convert ttl string to seconds |
| | |
| | | { |
| | | if ($this->type == 'db' && $this->db && $this->ttl) { |
| | | $this->db->query( |
| | | "DELETE FROM ".$this->db->table_name('cache'). |
| | | "DELETE FROM ".$this->table. |
| | | " WHERE user_id = ?". |
| | | " AND cache_key LIKE ?". |
| | | " AND " . $this->db->unixtimestamp('created')." < ?", |
| | | " AND expires < " . $this->db->now(), |
| | | $this->userid, |
| | | $this->prefix.'.%', |
| | | time() - $this->ttl); |
| | | $this->prefix.'.%'); |
| | | } |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Remove expired records of all caches |
| | | */ |
| | | static function gc() |
| | | { |
| | | $rcube = rcube::get_instance(); |
| | | $db = $rcube->get_dbh(); |
| | | |
| | | $db->query("DELETE FROM " . $db->table_name('cache') . " WHERE expires < " . $db->now()); |
| | | } |
| | | |
| | | |
| | |
| | | else { |
| | | $sql_result = $this->db->limitquery( |
| | | "SELECT data, cache_key". |
| | | " FROM ".$this->db->table_name('cache'). |
| | | " FROM " . $this->table. |
| | | " WHERE user_id = ?". |
| | | " AND cache_key = ?". |
| | | // for better performance we allow more records for one key |
| | |
| | | // Remove NULL rows (here we don't need to check if the record exist) |
| | | if ($data == 'N;') { |
| | | $this->db->query( |
| | | "DELETE FROM ".$this->db->table_name('cache'). |
| | | "DELETE FROM " . $this->table. |
| | | " WHERE user_id = ?". |
| | | " AND cache_key = ?", |
| | | $this->userid, $key); |
| | |
| | | // update existing cache record |
| | | if ($key_exists) { |
| | | $result = $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache'). |
| | | " SET created = ". $this->db->now().", data = ?". |
| | | "UPDATE " . $this->table. |
| | | " SET created = " . $this->db->now(). |
| | | ", expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL'). |
| | | ", data = ?". |
| | | " WHERE user_id = ?". |
| | | " AND cache_key = ?", |
| | | $data, $this->userid, $key); |
| | |
| | | // for better performance we allow more records for one key |
| | | // so, no need to check if record exist (see rcube_cache::read_record()) |
| | | $result = $this->db->query( |
| | | "INSERT INTO ".$this->db->table_name('cache'). |
| | | " (created, user_id, cache_key, data)". |
| | | " VALUES (".$this->db->now().", ?, ?, ?)", |
| | | "INSERT INTO " . $this->table. |
| | | " (created, expires, user_id, cache_key, data)". |
| | | " VALUES (" . $this->db->now() . ", " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') . ", ?, ?, ?)", |
| | | $this->userid, $key, $data); |
| | | } |
| | | |
| | |
| | | } |
| | | |
| | | $this->db->query( |
| | | "DELETE FROM ".$this->db->table_name('cache'). |
| | | "DELETE FROM " . $this->table. |
| | | " WHERE user_id = ?" . $where, |
| | | $this->userid); |
| | | } |
| | |
| | | $this->db->query( |
| | | "DELETE FROM " . $this->table |
| | | . " WHERE cache_key LIKE ?" |
| | | . " AND " . $this->db->unixtimestamp('created') . " < ?", |
| | | $this->prefix . '.%', |
| | | time() - $this->ttl); |
| | | . " AND expires < " . $this->db->now(), |
| | | $this->prefix . '.%'); |
| | | } |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Remove expired records of all caches |
| | | */ |
| | | static function gc() |
| | | { |
| | | $rcube = rcube::get_instance(); |
| | | $db = $rcube->get_dbh(); |
| | | |
| | | $db->query("DELETE FROM " . $db->table_name('cache_shared') . " WHERE expires < " . $db->now()); |
| | | } |
| | | |
| | | |
| | |
| | | if ($key_exists) { |
| | | $result = $this->db->query( |
| | | "UPDATE " . $this->table . |
| | | " SET created = " . $this->db->now() . ", data = ?" . |
| | | " SET created = " . $this->db->now() . |
| | | ", expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') . |
| | | ", data = ?". |
| | | " WHERE cache_key = ?", |
| | | $data, $key); |
| | | } |
| | |
| | | // so, no need to check if record exist (see rcube_cache::read_record()) |
| | | $result = $this->db->query( |
| | | "INSERT INTO ".$this->table. |
| | | " (created, cache_key, data)". |
| | | " VALUES (".$this->db->now().", ?, ?)", |
| | | " (created, expires, cache_key, data)". |
| | | " VALUES (".$this->db->now().", " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') . ", ?, ?)", |
| | | $key, $data); |
| | | } |
| | | |
| | |
| | | if ($interval) { |
| | | $add = ' ' . ($interval > 0 ? '+' : '-') . ' INTERVAL '; |
| | | $add .= $interval > 0 ? intval($interval) : intval($interval) * -1; |
| | | $add .= ' SECONDS'; |
| | | $add .= ' SECOND'; |
| | | } |
| | | |
| | | return "now()" . $add; |
| | |
| | | } |
| | | } |
| | | |
| | | /** |
| | | * Delete outdated cache entries |
| | | */ |
| | | public function expunge_cache() |
| | | { |
| | | if ($this->mcache) { |
| | | $ttl = rcube::get_instance()->config->get('messages_cache_ttl', '10d'); |
| | | $this->mcache->expunge($ttl); |
| | | } |
| | | |
| | | /* |
| | | // this cache is expunged by rcube class |
| | | if ($this->cache) { |
| | | $this->cache->expunge(); |
| | | } |
| | | */ |
| | | } |
| | | |
| | | |
| | | /* -------------------------------- |
| | | * message caching methods |
| | |
| | | if ($this->messages_caching && !$this->mcache) { |
| | | $rcube = rcube::get_instance(); |
| | | if (($dbh = $rcube->get_dbh()) && ($userid = $rcube->get_user_id())) { |
| | | $ttl = $rcube->config->get('messages_cache_ttl', '10d'); |
| | | $this->mcache = new rcube_imap_cache( |
| | | $dbh, $this, $userid, $this->options['skip_deleted']); |
| | | $dbh, $this, $userid, $this->options['skip_deleted'], $ttl); |
| | | } |
| | | } |
| | | |
| | |
| | | } |
| | | |
| | | |
| | | /** |
| | | * Delete outdated cache entries |
| | | */ |
| | | function cache_gc() |
| | | { |
| | | rcube_imap_cache::gc(); |
| | | } |
| | | |
| | | |
| | | /* -------------------------------- |
| | | * protected methods |
| | | * --------------------------------*/ |
| | |
| | | private $userid; |
| | | |
| | | /** |
| | | * Expiration time in seconds |
| | | * |
| | | * @var int |
| | | */ |
| | | private $ttl; |
| | | |
| | | /** |
| | | * Internal (in-memory) cache |
| | | * |
| | | * @var array |
| | |
| | | |
| | | /** |
| | | * Object constructor. |
| | | * |
| | | * @param rcube_db $db DB handler |
| | | * @param rcube_imap $imap IMAP handler |
| | | * @param int $userid User identifier |
| | | * @param bool $skip_deleted skip_deleted flag |
| | | * @param string $ttl Expiration time of memcache/apc items |
| | | * |
| | | */ |
| | | function __construct($db, $imap, $userid, $skip_deleted) |
| | | function __construct($db, $imap, $userid, $skip_deleted, $ttl=0) |
| | | { |
| | | // convert ttl string to seconds |
| | | $ttl = get_offset_sec($ttl); |
| | | if ($ttl > 2592000) $ttl = 2592000; |
| | | |
| | | $this->db = $db; |
| | | $this->imap = $imap; |
| | | $this->userid = $userid; |
| | | $this->skip_deleted = $skip_deleted; |
| | | $this->ttl = $ttl; |
| | | } |
| | | |
| | | |
| | |
| | | if (!$force) { |
| | | $res = $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_messages') |
| | | ." SET flags = ?, data = ?, changed = ".$this->db->now() |
| | | ." SET flags = ?, data = ?, expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?" |
| | | ." AND uid = ?", |
| | |
| | | // insert new record |
| | | $res = $this->db->query( |
| | | "INSERT INTO ".$this->db->table_name('cache_messages') |
| | | ." (user_id, mailbox, uid, flags, changed, data)" |
| | | ." VALUES (?, ?, ?, ?, ".$this->db->now().", ?)", |
| | | ." (user_id, mailbox, uid, flags, expires, data)" |
| | | ." VALUES (?, ?, ?, ?, ". ($this->ttl ? $this->db->now($this->ttl) : 'NULL') . ", ?)", |
| | | $this->userid, $mailbox, (int) $message->uid, $flags, $msg); |
| | | |
| | | // race-condition, insert failed so try update (#1489146) |
| | |
| | | if ($force && !$res && !$this->db->is_error($res)) { |
| | | $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_messages') |
| | | ." SET flags = ?, data = ?, changed = ".$this->db->now() |
| | | ." SET expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | .", flags = ?, data = ?" |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?" |
| | | ." AND uid = ?", |
| | |
| | | |
| | | $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_messages') |
| | | ." SET changed = ".$this->db->now() |
| | | ." SET expires = ". ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | .", flags = flags ".($enabled ? "+ $idx" : "- $idx") |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?" |
| | |
| | | |
| | | |
| | | /** |
| | | * Delete cache entries older than TTL |
| | | * |
| | | * @param string $ttl Lifetime of message cache entries |
| | | * Delete expired cache entries |
| | | */ |
| | | function expunge($ttl) |
| | | static function gc() |
| | | { |
| | | // get expiration timestamp |
| | | $ts = get_offset_time($ttl, -1); |
| | | $rcube = rcube::get_instance(); |
| | | $db = $rcube->get_dbh(); |
| | | |
| | | $this->db->query("DELETE FROM ".$this->db->table_name('cache_messages') |
| | | ." WHERE changed < " . $this->db->fromunixtime($ts)); |
| | | $db->query("DELETE FROM ".$db->table_name('cache_messages') |
| | | ." WHERE expired < " . $db->now()); |
| | | |
| | | $this->db->query("DELETE FROM ".$this->db->table_name('cache_index') |
| | | ." WHERE changed < " . $this->db->fromunixtime($ts)); |
| | | $db->query("DELETE FROM ".$db->table_name('cache_index') |
| | | ." WHERE expired < " . $db->now()); |
| | | |
| | | $this->db->query("DELETE FROM ".$this->db->table_name('cache_thread') |
| | | ." WHERE changed < " . $this->db->fromunixtime($ts)); |
| | | $db->query("DELETE FROM ".$db->table_name('cache_thread') |
| | | ." WHERE expired < " . $db->now()); |
| | | } |
| | | |
| | | |
| | |
| | | if ($exists) { |
| | | $res = $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_index') |
| | | ." SET data = ?, valid = 1, changed = ".$this->db->now() |
| | | ." SET data = ?, valid = 1, expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?", |
| | | $data, $this->userid, $mailbox); |
| | |
| | | |
| | | $res = $this->db->query( |
| | | "INSERT INTO ".$this->db->table_name('cache_index') |
| | | ." (user_id, mailbox, data, valid, changed)" |
| | | ." VALUES (?, ?, ?, 1, ".$this->db->now().")", |
| | | ." (user_id, mailbox, valid, expires, data)" |
| | | ." VALUES (?, ?, 1, ". ($this->ttl ? $this->db->now($this->ttl) : 'NULL') .", ?)", |
| | | $this->userid, $mailbox, $data); |
| | | |
| | | // race-condition, insert failed so try update (#1489146) |
| | |
| | | if (!$exists && !$res && !$this->db->is_error($res)) { |
| | | $res = $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_index') |
| | | ." SET data = ?, valid = 1, changed = ".$this->db->now() |
| | | ." SET data = ?, valid = 1, expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?", |
| | | $data, $this->userid, $mailbox); |
| | |
| | | ); |
| | | $data = implode('@', $data); |
| | | |
| | | $expires = ($this->ttl ? $this->db->now($this->ttl) : 'NULL'); |
| | | |
| | | if ($exists) { |
| | | $res = $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_thread') |
| | | ." SET data = ?, changed = ".$this->db->now() |
| | | ." SET data = ?, expires = $expires" |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?", |
| | | $data, $this->userid, $mailbox); |
| | |
| | | |
| | | $res = $this->db->query( |
| | | "INSERT INTO ".$this->db->table_name('cache_thread') |
| | | ." (user_id, mailbox, data, changed)" |
| | | ." VALUES (?, ?, ?, ".$this->db->now().")", |
| | | ." (user_id, mailbox, expires, data)" |
| | | ." VALUES (?, ?, $expires, ?)", |
| | | $this->userid, $mailbox, $data); |
| | | |
| | | // race-condition, insert failed so try update (#1489146) |
| | |
| | | if (!$exists && !$res && !$this->db->is_error($res)) { |
| | | $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_thread') |
| | | ." SET data = ?, changed = ".$this->db->now() |
| | | ." SET expires = $expires, data = ?" |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?", |
| | | $data, $this->userid, $mailbox); |
| | |
| | | |
| | | $this->db->query( |
| | | "UPDATE ".$this->db->table_name('cache_messages') |
| | | ." SET flags = ?, changed = ".$this->db->now() |
| | | ." SET flags = ?, expires = " . ($this->ttl ? $this->db->now($this->ttl) : 'NULL') |
| | | ." WHERE user_id = ?" |
| | | ." AND mailbox = ?" |
| | | ." AND uid = ?" |
| | |
| | | /** |
| | | * Delete outdated cache entries |
| | | */ |
| | | abstract function expunge_cache(); |
| | | abstract function cache_gc(); |
| | | |
| | | } // end class rcube_storage |