0001-misc-limit-query-to-recent-sessions-when-checking-fo.patch
wcs/sessions.py | ||
---|---|---|
14 | 14 |
# You should have received a copy of the GNU General Public License |
15 | 15 |
# along with this program; if not, see <http://www.gnu.org/licenses/>. |
16 | 16 | |
17 |
import os |
|
17 | 18 |
import time |
18 | 19 |
import uuid |
19 | 20 | |
... | ... | |
72 | 73 |
del self.visiting_objects[object_key] |
73 | 74 |
self.visiting_objects[key] = current_timestamp |
74 | 75 | |
76 |
@classmethod |
|
77 |
def select_recent(cls, seconds=30*60, **kwargs): |
|
78 |
objects_dir = cls.get_objects_dir() |
|
79 |
if not os.path.exists(objects_dir): |
|
80 |
return [] |
|
81 |
ids = [] |
|
82 |
time_limit = time.time() - seconds |
|
83 |
for filename in os.listdir(objects_dir): |
|
84 |
if filename[0] == '.': |
|
85 |
continue |
|
86 |
if os.stat(os.path.join(objects_dir, filename)).st_mtime > time_limit: |
|
87 |
ids.append(filename) |
|
88 |
return cls.get_ids(ids, **kwargs) |
|
89 | ||
75 | 90 |
@classmethod |
76 | 91 |
def get_visited_objects(cls, exclude_user=None): |
77 | 92 |
# return the list of visited objects |
78 | 93 |
current_timestamp = time.time() |
79 | 94 |
visited_objects = {} |
80 |
for session in cls.select(ignore_errors=True): |
|
95 |
for session in cls.select_recent(ignore_errors=True):
|
|
81 | 96 |
if session.user and session.user == exclude_user: |
82 | 97 |
continue |
83 | 98 |
visiting_objects = getattr(session, 'visiting_objects', None) |
... | ... | |
90 | 105 | |
91 | 106 |
@classmethod |
92 | 107 |
def get_sessions_with_visited_object(cls, object_key): |
93 |
for session in cls.select(ignore_errors=True): |
|
108 |
for session in cls.select_recent(ignore_errors=True):
|
|
94 | 109 |
visiting_objects = getattr(session, 'visiting_objects', None) |
95 | 110 |
if not visiting_objects: |
96 | 111 |
continue |
... | ... | |
114 | 129 |
if object_key in (getattr(self, 'visiting_objects', None) or {}): |
115 | 130 |
del self.visiting_objects[object_key] |
116 | 131 |
# and from others |
117 |
for session in self.__class__.select(ignore_errors=True): |
|
132 |
for session in self.__class__.select_recent(ignore_errors=True):
|
|
118 | 133 |
if session.id == self.id: |
119 | 134 |
continue |
120 | 135 |
visiting_objects = getattr(session, 'visiting_objects', None) |
wcs/sql.py | ||
---|---|---|
659 | 659 |
AND table_name = %s''', (table_name,)) |
660 | 660 |
existing_fields = set([x[0] for x in cur.fetchall()]) |
661 | 661 | |
662 |
needed_fields = set(['id', 'session_data', 'name_identifier', 'visiting_objects_keys']) |
|
662 |
needed_fields = set(['id', 'session_data', 'name_identifier', |
|
663 |
'visiting_objects_keys', 'last_update_time']) |
|
664 | ||
665 |
# migrations |
|
666 |
if not 'last_update_time' in existing_fields: |
|
667 |
cur.execute('''ALTER TABLE %s ADD COLUMN last_update_time timestamp DEFAULT NOW()''' % table_name) |
|
668 |
cur.execute('''CREATE INDEX %s_ts ON %s (last_update_time)''' % ( |
|
669 |
table_name, table_name)) |
|
663 | 670 | |
664 | 671 |
# delete obsolete fields |
665 | 672 |
for field in (existing_fields - needed_fields): |
... | ... | |
1819 | 1826 |
('session_data', 'bytea'), |
1820 | 1827 |
] |
1821 | 1828 | |
1829 |
@classmethod |
|
1830 |
@guard_postgres |
|
1831 |
def select_recent(cls, seconds=30*60, **kwargs): |
|
1832 |
clause = [GreaterOrEqual('last_update_time', datetime.datetime.now() - datetime.timedelta(seconds=seconds))] |
|
1833 |
return cls.select(clause=clause, **kwargs) |
|
1834 | ||
1822 | 1835 |
@guard_postgres |
1823 | 1836 |
def store(self): |
1824 | 1837 |
sql_dict = { |
... | ... | |
1828 | 1841 |
# table, they are ignored when loading the data. |
1829 | 1842 |
'name_identifier': self.name_identifier, |
1830 | 1843 |
'visiting_objects_keys': self.visiting_objects.keys() if getattr(self, 'visiting_objects') else None, |
1844 |
'last_update_time': datetime.datetime.now(), |
|
1831 | 1845 |
} |
1832 | 1846 | |
1833 | 1847 |
conn, cur = get_connection_and_cursor() |
... | ... | |
1877 | 1891 | |
1878 | 1892 |
sql_statement = '''SELECT %s |
1879 | 1893 |
FROM %s |
1880 |
WHERE %%(value)s = ANY(visiting_objects_keys)''' % ( |
|
1894 |
WHERE %%(value)s = ANY(visiting_objects_keys) |
|
1895 |
AND last_update_time > (now() - interval '30 minutes') |
|
1896 |
''' % ( |
|
1881 | 1897 |
', '.join([x[0] for x in cls._table_static_fields] |
1882 | 1898 |
+ cls.get_data_fields()), |
1883 | 1899 |
cls._table_name) |
... | ... | |
2174 | 2190 |
return result |
2175 | 2191 | |
2176 | 2192 | |
2177 |
SQL_LEVEL = 31
|
|
2193 |
SQL_LEVEL = 32
|
|
2178 | 2194 | |
2179 | 2195 |
def migrate_global_views(conn, cur): |
2180 | 2196 |
cur.execute('''SELECT COUNT(*) FROM information_schema.tables |
... | ... | |
2291 | 2307 |
# 24: add index on evolution(formdata_id) |
2292 | 2308 |
for formdef in FormDef.select(): |
2293 | 2309 |
do_formdef_indexes(formdef, created=False, conn=conn, cur=cur) |
2294 |
if sql_level < 25: |
|
2310 |
if sql_level < 32: |
|
2311 |
# 25: create session_table |
|
2312 |
# 32: add last_update_time column to session table |
|
2295 | 2313 |
do_session_table() |
2296 | 2314 |
if sql_level < 30: |
2297 | 2315 |
# 30: actually remove evo.who on anonymised formdatas |
2298 |
- |