-
Notifications
You must be signed in to change notification settings - Fork 348
/
Copy pathextension.py
126 lines (105 loc) · 4.71 KB
/
extension.py
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
# Licensed to the Apache Software Foundation (ASF) under one or more
# contributor license agreements. See the NOTICE file distributed with
# this work for additional information regarding copyright ownership.
# The ASF licenses this file to You under the Apache License, Version 2.0
# (the "License"); you may not use this file except in compliance with
# the License. You may obtain a copy of the License at
#
# http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS,
# WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
# See the License for the specific language governing permissions and
# limitations under the License.
"""Session Config Extension
Configures redis or memcached for session sharing
Simply create a service instance called either `redis-sessions` or
`memcached-sessions`, bind it to the app, and the extension takes care of
the rest.
"""
from extension_helpers import PHPExtensionHelper
class BaseSetup(object):
def __init__(self, ctx, info):
self._ctx = ctx
self._info = info
self.creds = self._info.get('credentials', {})
def session_store_key(self):
key_name = self.DEFAULT_SESSION_STORE_TRIGGER
if self.CUSTOM_SESSION_STORE_KEY_NAME in self._ctx:
key_name = self._ctx[self.CUSTOM_SESSION_STORE_KEY_NAME]
return key_name
def custom_config_php_ini(self, php_ini):
pass
class RedisSetup(BaseSetup):
DEFAULT_SESSION_STORE_TRIGGER = 'redis-sessions'
CUSTOM_SESSION_STORE_KEY_NAME = 'REDIS_SESSION_STORE_SERVICE_NAME'
EXTENSION_NAME = 'redis'
def __init__(self, ctx, info):
BaseSetup.__init__(self, ctx, info)
def session_save_path(self):
return "tcp://%s:%s?auth=%s" % (
self.creds.get('hostname',
self.creds.get('host', 'not-found')),
self.creds.get('port', 'not-found'),
self.creds.get('password', ''))
class MemcachedSetup(BaseSetup):
DEFAULT_SESSION_STORE_TRIGGER = 'memcached-sessions'
CUSTOM_SESSION_STORE_KEY_NAME = 'MEMCACHED_SESSION_STORE_SERVICE_NAME'
EXTENSION_NAME = 'memcached'
def __init__(self, ctx, info):
BaseSetup.__init__(self, ctx, info)
def session_save_path(self):
return 'PERSISTENT=app_sessions %s' % self.creds.get('servers',
'not-found')
def custom_config_php_ini(self, php_ini):
php_ini.append_lines([
'memcached.sess_binary=On\n',
'memcached.use_sasl=On\n',
'memcached.sess_sasl_username=%s\n' % self.creds.get('username',
''),
'memcached.sess_sasl_password=%s\n' % self.creds.get('password', '')
])
class SessionStoreConfig(PHPExtensionHelper):
def __init__(self, ctx):
PHPExtensionHelper.__init__(self, ctx)
self.service = None
def _should_compile(self):
if self.service is None:
self.service = self._load_session()
return self.service is not None
def _load_session(self):
# load search keys
session_types = [
RedisSetup,
MemcachedSetup
]
# search for an appropriately name session store
vcap_services = self._ctx.get('VCAP_SERVICES', {})
for provider, services in vcap_services.items():
for service in services:
service_name = service.get('name', '')
for session_type in session_types:
session = session_type(self._ctx, service)
if service_name.find(session.session_store_key()) != -1:
return session
def _configure(self):
# load the PHP extension that provides session save handler
if self.service is not None:
self._ctx.get('PHP_EXTENSIONS',
[]).append(self.service.EXTENSION_NAME)
def _compile(self, install):
# modify php.ini to contain the right session config
self.load_config()
self._php_ini.update_lines(
r'^session\.name = JSESSIONID$',
'session.name = PHPSESSIONID')
self._php_ini.update_lines(
r'^session\.save_handler = files$',
'session.save_handler = %s' % self.service.EXTENSION_NAME)
self._php_ini.update_lines(
r'^session\.save_path = "@{TMPDIR}"$',
'session.save_path = "%s"' % self.service.session_save_path())
self.service.custom_config_php_ini(self._php_ini)
self._php_ini.save(self._php_ini_path)
SessionStoreConfig.register(__name__)