##// END OF EJS Templates
config: removed vcsserver log_level deprecated option.
marcink -
r4168:2a769b0d default
parent child Browse files
Show More
@@ -1,754 +1,753 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2
2
3 # Copyright (C) 2010-2019 RhodeCode GmbH
3 # Copyright (C) 2010-2019 RhodeCode GmbH
4 #
4 #
5 # This program is free software: you can redistribute it and/or modify
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
7 # (only), as published by the Free Software Foundation.
8 #
8 #
9 # This program is distributed in the hope that it will be useful,
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
12 # GNU General Public License for more details.
13 #
13 #
14 # You should have received a copy of the GNU Affero General Public License
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
16 #
17 # This program is dual-licensed. If you wish to learn more about the
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
20
21 import os
21 import os
22 import sys
22 import sys
23 import logging
23 import logging
24 import collections
24 import collections
25 import tempfile
25 import tempfile
26 import time
26 import time
27
27
28 from paste.gzipper import make_gzip_middleware
28 from paste.gzipper import make_gzip_middleware
29 import pyramid.events
29 import pyramid.events
30 from pyramid.wsgi import wsgiapp
30 from pyramid.wsgi import wsgiapp
31 from pyramid.authorization import ACLAuthorizationPolicy
31 from pyramid.authorization import ACLAuthorizationPolicy
32 from pyramid.config import Configurator
32 from pyramid.config import Configurator
33 from pyramid.settings import asbool, aslist
33 from pyramid.settings import asbool, aslist
34 from pyramid.httpexceptions import (
34 from pyramid.httpexceptions import (
35 HTTPException, HTTPError, HTTPInternalServerError, HTTPFound, HTTPNotFound)
35 HTTPException, HTTPError, HTTPInternalServerError, HTTPFound, HTTPNotFound)
36 from pyramid.renderers import render_to_response
36 from pyramid.renderers import render_to_response
37
37
38 from rhodecode.model import meta
38 from rhodecode.model import meta
39 from rhodecode.config import patches
39 from rhodecode.config import patches
40 from rhodecode.config import utils as config_utils
40 from rhodecode.config import utils as config_utils
41 from rhodecode.config.environment import load_pyramid_environment
41 from rhodecode.config.environment import load_pyramid_environment
42
42
43 import rhodecode.events
43 import rhodecode.events
44 from rhodecode.lib.middleware.vcs import VCSMiddleware
44 from rhodecode.lib.middleware.vcs import VCSMiddleware
45 from rhodecode.lib.request import Request
45 from rhodecode.lib.request import Request
46 from rhodecode.lib.vcs import VCSCommunicationError
46 from rhodecode.lib.vcs import VCSCommunicationError
47 from rhodecode.lib.exceptions import VCSServerUnavailable
47 from rhodecode.lib.exceptions import VCSServerUnavailable
48 from rhodecode.lib.middleware.appenlight import wrap_in_appenlight_if_enabled
48 from rhodecode.lib.middleware.appenlight import wrap_in_appenlight_if_enabled
49 from rhodecode.lib.middleware.https_fixup import HttpsFixup
49 from rhodecode.lib.middleware.https_fixup import HttpsFixup
50 from rhodecode.lib.celerylib.loader import configure_celery
50 from rhodecode.lib.celerylib.loader import configure_celery
51 from rhodecode.lib.plugins.utils import register_rhodecode_plugin
51 from rhodecode.lib.plugins.utils import register_rhodecode_plugin
52 from rhodecode.lib.utils2 import aslist as rhodecode_aslist, AttributeDict
52 from rhodecode.lib.utils2 import aslist as rhodecode_aslist, AttributeDict
53 from rhodecode.lib.exc_tracking import store_exception
53 from rhodecode.lib.exc_tracking import store_exception
54 from rhodecode.subscribers import (
54 from rhodecode.subscribers import (
55 scan_repositories_if_enabled, write_js_routes_if_enabled,
55 scan_repositories_if_enabled, write_js_routes_if_enabled,
56 write_metadata_if_needed, inject_app_settings)
56 write_metadata_if_needed, inject_app_settings)
57
57
58
58
59 log = logging.getLogger(__name__)
59 log = logging.getLogger(__name__)
60
60
61
61
62 def is_http_error(response):
62 def is_http_error(response):
63 # error which should have traceback
63 # error which should have traceback
64 return response.status_code > 499
64 return response.status_code > 499
65
65
66
66
67 def should_load_all():
67 def should_load_all():
68 """
68 """
69 Returns if all application components should be loaded. In some cases it's
69 Returns if all application components should be loaded. In some cases it's
70 desired to skip apps loading for faster shell script execution
70 desired to skip apps loading for faster shell script execution
71 """
71 """
72 ssh_cmd = os.environ.get('RC_CMD_SSH_WRAPPER')
72 ssh_cmd = os.environ.get('RC_CMD_SSH_WRAPPER')
73 if ssh_cmd:
73 if ssh_cmd:
74 return False
74 return False
75
75
76 return True
76 return True
77
77
78
78
79 def make_pyramid_app(global_config, **settings):
79 def make_pyramid_app(global_config, **settings):
80 """
80 """
81 Constructs the WSGI application based on Pyramid.
81 Constructs the WSGI application based on Pyramid.
82
82
83 Specials:
83 Specials:
84
84
85 * The application can also be integrated like a plugin via the call to
85 * The application can also be integrated like a plugin via the call to
86 `includeme`. This is accompanied with the other utility functions which
86 `includeme`. This is accompanied with the other utility functions which
87 are called. Changing this should be done with great care to not break
87 are called. Changing this should be done with great care to not break
88 cases when these fragments are assembled from another place.
88 cases when these fragments are assembled from another place.
89
89
90 """
90 """
91
91
92 # Allows to use format style "{ENV_NAME}" placeholders in the configuration. It
92 # Allows to use format style "{ENV_NAME}" placeholders in the configuration. It
93 # will be replaced by the value of the environment variable "NAME" in this case.
93 # will be replaced by the value of the environment variable "NAME" in this case.
94 start_time = time.time()
94 start_time = time.time()
95
95
96 debug = asbool(global_config.get('debug'))
96 debug = asbool(global_config.get('debug'))
97 if debug:
97 if debug:
98 enable_debug()
98 enable_debug()
99
99
100 environ = {'ENV_{}'.format(key): value for key, value in os.environ.items()}
100 environ = {'ENV_{}'.format(key): value for key, value in os.environ.items()}
101
101
102 global_config = _substitute_values(global_config, environ)
102 global_config = _substitute_values(global_config, environ)
103 settings = _substitute_values(settings, environ)
103 settings = _substitute_values(settings, environ)
104
104
105 sanitize_settings_and_apply_defaults(global_config, settings)
105 sanitize_settings_and_apply_defaults(global_config, settings)
106
106
107 config = Configurator(settings=settings)
107 config = Configurator(settings=settings)
108
108
109 # Apply compatibility patches
109 # Apply compatibility patches
110 patches.inspect_getargspec()
110 patches.inspect_getargspec()
111
111
112 load_pyramid_environment(global_config, settings)
112 load_pyramid_environment(global_config, settings)
113
113
114 # Static file view comes first
114 # Static file view comes first
115 includeme_first(config)
115 includeme_first(config)
116
116
117 includeme(config)
117 includeme(config)
118
118
119 pyramid_app = config.make_wsgi_app()
119 pyramid_app = config.make_wsgi_app()
120 pyramid_app = wrap_app_in_wsgi_middlewares(pyramid_app, config)
120 pyramid_app = wrap_app_in_wsgi_middlewares(pyramid_app, config)
121 pyramid_app.config = config
121 pyramid_app.config = config
122
122
123 config.configure_celery(global_config['__file__'])
123 config.configure_celery(global_config['__file__'])
124 # creating the app uses a connection - return it after we are done
124 # creating the app uses a connection - return it after we are done
125 meta.Session.remove()
125 meta.Session.remove()
126 total_time = time.time() - start_time
126 total_time = time.time() - start_time
127 log.info('Pyramid app `%s` created and configured in %.2fs',
127 log.info('Pyramid app `%s` created and configured in %.2fs',
128 pyramid_app.func_name, total_time)
128 pyramid_app.func_name, total_time)
129
129
130 return pyramid_app
130 return pyramid_app
131
131
132
132
133 def not_found_view(request):
133 def not_found_view(request):
134 """
134 """
135 This creates the view which should be registered as not-found-view to
135 This creates the view which should be registered as not-found-view to
136 pyramid.
136 pyramid.
137 """
137 """
138
138
139 if not getattr(request, 'vcs_call', None):
139 if not getattr(request, 'vcs_call', None):
140 # handle like regular case with our error_handler
140 # handle like regular case with our error_handler
141 return error_handler(HTTPNotFound(), request)
141 return error_handler(HTTPNotFound(), request)
142
142
143 # handle not found view as a vcs call
143 # handle not found view as a vcs call
144 settings = request.registry.settings
144 settings = request.registry.settings
145 ae_client = getattr(request, 'ae_client', None)
145 ae_client = getattr(request, 'ae_client', None)
146 vcs_app = VCSMiddleware(
146 vcs_app = VCSMiddleware(
147 HTTPNotFound(), request.registry, settings,
147 HTTPNotFound(), request.registry, settings,
148 appenlight_client=ae_client)
148 appenlight_client=ae_client)
149
149
150 return wsgiapp(vcs_app)(None, request)
150 return wsgiapp(vcs_app)(None, request)
151
151
152
152
153 def error_handler(exception, request):
153 def error_handler(exception, request):
154 import rhodecode
154 import rhodecode
155 from rhodecode.lib import helpers
155 from rhodecode.lib import helpers
156
156
157 rhodecode_title = rhodecode.CONFIG.get('rhodecode_title') or 'RhodeCode'
157 rhodecode_title = rhodecode.CONFIG.get('rhodecode_title') or 'RhodeCode'
158
158
159 base_response = HTTPInternalServerError()
159 base_response = HTTPInternalServerError()
160 # prefer original exception for the response since it may have headers set
160 # prefer original exception for the response since it may have headers set
161 if isinstance(exception, HTTPException):
161 if isinstance(exception, HTTPException):
162 base_response = exception
162 base_response = exception
163 elif isinstance(exception, VCSCommunicationError):
163 elif isinstance(exception, VCSCommunicationError):
164 base_response = VCSServerUnavailable()
164 base_response = VCSServerUnavailable()
165
165
166 if is_http_error(base_response):
166 if is_http_error(base_response):
167 log.exception(
167 log.exception(
168 'error occurred handling this request for path: %s', request.path)
168 'error occurred handling this request for path: %s', request.path)
169
169
170 error_explanation = base_response.explanation or str(base_response)
170 error_explanation = base_response.explanation or str(base_response)
171 if base_response.status_code == 404:
171 if base_response.status_code == 404:
172 error_explanation += " Optionally you don't have permission to access this page."
172 error_explanation += " Optionally you don't have permission to access this page."
173 c = AttributeDict()
173 c = AttributeDict()
174 c.error_message = base_response.status
174 c.error_message = base_response.status
175 c.error_explanation = error_explanation
175 c.error_explanation = error_explanation
176 c.visual = AttributeDict()
176 c.visual = AttributeDict()
177
177
178 c.visual.rhodecode_support_url = (
178 c.visual.rhodecode_support_url = (
179 request.registry.settings.get('rhodecode_support_url') or
179 request.registry.settings.get('rhodecode_support_url') or
180 request.route_url('rhodecode_support')
180 request.route_url('rhodecode_support')
181 )
181 )
182 c.redirect_time = 0
182 c.redirect_time = 0
183 c.rhodecode_name = rhodecode_title
183 c.rhodecode_name = rhodecode_title
184 if not c.rhodecode_name:
184 if not c.rhodecode_name:
185 c.rhodecode_name = 'Rhodecode'
185 c.rhodecode_name = 'Rhodecode'
186
186
187 c.causes = []
187 c.causes = []
188 if is_http_error(base_response):
188 if is_http_error(base_response):
189 c.causes.append('Server is overloaded.')
189 c.causes.append('Server is overloaded.')
190 c.causes.append('Server database connection is lost.')
190 c.causes.append('Server database connection is lost.')
191 c.causes.append('Server expected unhandled error.')
191 c.causes.append('Server expected unhandled error.')
192
192
193 if hasattr(base_response, 'causes'):
193 if hasattr(base_response, 'causes'):
194 c.causes = base_response.causes
194 c.causes = base_response.causes
195
195
196 c.messages = helpers.flash.pop_messages(request=request)
196 c.messages = helpers.flash.pop_messages(request=request)
197
197
198 exc_info = sys.exc_info()
198 exc_info = sys.exc_info()
199 c.exception_id = id(exc_info)
199 c.exception_id = id(exc_info)
200 c.show_exception_id = isinstance(base_response, VCSServerUnavailable) \
200 c.show_exception_id = isinstance(base_response, VCSServerUnavailable) \
201 or base_response.status_code > 499
201 or base_response.status_code > 499
202 c.exception_id_url = request.route_url(
202 c.exception_id_url = request.route_url(
203 'admin_settings_exception_tracker_show', exception_id=c.exception_id)
203 'admin_settings_exception_tracker_show', exception_id=c.exception_id)
204
204
205 if c.show_exception_id:
205 if c.show_exception_id:
206 store_exception(c.exception_id, exc_info)
206 store_exception(c.exception_id, exc_info)
207
207
208 response = render_to_response(
208 response = render_to_response(
209 '/errors/error_document.mako', {'c': c, 'h': helpers}, request=request,
209 '/errors/error_document.mako', {'c': c, 'h': helpers}, request=request,
210 response=base_response)
210 response=base_response)
211
211
212 return response
212 return response
213
213
214
214
215 def includeme_first(config):
215 def includeme_first(config):
216 # redirect automatic browser favicon.ico requests to correct place
216 # redirect automatic browser favicon.ico requests to correct place
217 def favicon_redirect(context, request):
217 def favicon_redirect(context, request):
218 return HTTPFound(
218 return HTTPFound(
219 request.static_path('rhodecode:public/images/favicon.ico'))
219 request.static_path('rhodecode:public/images/favicon.ico'))
220
220
221 config.add_view(favicon_redirect, route_name='favicon')
221 config.add_view(favicon_redirect, route_name='favicon')
222 config.add_route('favicon', '/favicon.ico')
222 config.add_route('favicon', '/favicon.ico')
223
223
224 def robots_redirect(context, request):
224 def robots_redirect(context, request):
225 return HTTPFound(
225 return HTTPFound(
226 request.static_path('rhodecode:public/robots.txt'))
226 request.static_path('rhodecode:public/robots.txt'))
227
227
228 config.add_view(robots_redirect, route_name='robots')
228 config.add_view(robots_redirect, route_name='robots')
229 config.add_route('robots', '/robots.txt')
229 config.add_route('robots', '/robots.txt')
230
230
231 config.add_static_view(
231 config.add_static_view(
232 '_static/deform', 'deform:static')
232 '_static/deform', 'deform:static')
233 config.add_static_view(
233 config.add_static_view(
234 '_static/rhodecode', path='rhodecode:public', cache_max_age=3600 * 24)
234 '_static/rhodecode', path='rhodecode:public', cache_max_age=3600 * 24)
235
235
236
236
237 def includeme(config):
237 def includeme(config):
238 log.debug('Initializing main includeme from %s', os.path.basename(__file__))
238 log.debug('Initializing main includeme from %s', os.path.basename(__file__))
239 settings = config.registry.settings
239 settings = config.registry.settings
240 config.set_request_factory(Request)
240 config.set_request_factory(Request)
241
241
242 # plugin information
242 # plugin information
243 config.registry.rhodecode_plugins = collections.OrderedDict()
243 config.registry.rhodecode_plugins = collections.OrderedDict()
244
244
245 config.add_directive(
245 config.add_directive(
246 'register_rhodecode_plugin', register_rhodecode_plugin)
246 'register_rhodecode_plugin', register_rhodecode_plugin)
247
247
248 config.add_directive('configure_celery', configure_celery)
248 config.add_directive('configure_celery', configure_celery)
249
249
250 if asbool(settings.get('appenlight', 'false')):
250 if asbool(settings.get('appenlight', 'false')):
251 config.include('appenlight_client.ext.pyramid_tween')
251 config.include('appenlight_client.ext.pyramid_tween')
252
252
253 load_all = should_load_all()
253 load_all = should_load_all()
254
254
255 # Includes which are required. The application would fail without them.
255 # Includes which are required. The application would fail without them.
256 config.include('pyramid_mako')
256 config.include('pyramid_mako')
257 config.include('rhodecode.lib.rc_beaker')
257 config.include('rhodecode.lib.rc_beaker')
258 config.include('rhodecode.lib.rc_cache')
258 config.include('rhodecode.lib.rc_cache')
259
259
260 config.include('rhodecode.apps._base.navigation')
260 config.include('rhodecode.apps._base.navigation')
261 config.include('rhodecode.apps._base.subscribers')
261 config.include('rhodecode.apps._base.subscribers')
262 config.include('rhodecode.tweens')
262 config.include('rhodecode.tweens')
263 config.include('rhodecode.authentication')
263 config.include('rhodecode.authentication')
264
264
265 if load_all:
265 if load_all:
266 config.include('rhodecode.integrations')
266 config.include('rhodecode.integrations')
267
267
268 if load_all:
268 if load_all:
269 # load CE authentication plugins
269 # load CE authentication plugins
270 config.include('rhodecode.authentication.plugins.auth_crowd')
270 config.include('rhodecode.authentication.plugins.auth_crowd')
271 config.include('rhodecode.authentication.plugins.auth_headers')
271 config.include('rhodecode.authentication.plugins.auth_headers')
272 config.include('rhodecode.authentication.plugins.auth_jasig_cas')
272 config.include('rhodecode.authentication.plugins.auth_jasig_cas')
273 config.include('rhodecode.authentication.plugins.auth_ldap')
273 config.include('rhodecode.authentication.plugins.auth_ldap')
274 config.include('rhodecode.authentication.plugins.auth_pam')
274 config.include('rhodecode.authentication.plugins.auth_pam')
275 config.include('rhodecode.authentication.plugins.auth_rhodecode')
275 config.include('rhodecode.authentication.plugins.auth_rhodecode')
276 config.include('rhodecode.authentication.plugins.auth_token')
276 config.include('rhodecode.authentication.plugins.auth_token')
277
277
278 # Auto discover authentication plugins and include their configuration.
278 # Auto discover authentication plugins and include their configuration.
279 if asbool(settings.get('auth_plugin.import_legacy_plugins', 'true')):
279 if asbool(settings.get('auth_plugin.import_legacy_plugins', 'true')):
280 from rhodecode.authentication import discover_legacy_plugins
280 from rhodecode.authentication import discover_legacy_plugins
281 discover_legacy_plugins(config)
281 discover_legacy_plugins(config)
282
282
283 # apps
283 # apps
284 if load_all:
284 if load_all:
285 config.include('rhodecode.apps._base')
285 config.include('rhodecode.apps._base')
286 config.include('rhodecode.apps.hovercards')
286 config.include('rhodecode.apps.hovercards')
287 config.include('rhodecode.apps.ops')
287 config.include('rhodecode.apps.ops')
288 config.include('rhodecode.apps.admin')
288 config.include('rhodecode.apps.admin')
289 config.include('rhodecode.apps.channelstream')
289 config.include('rhodecode.apps.channelstream')
290 config.include('rhodecode.apps.file_store')
290 config.include('rhodecode.apps.file_store')
291 config.include('rhodecode.apps.login')
291 config.include('rhodecode.apps.login')
292 config.include('rhodecode.apps.home')
292 config.include('rhodecode.apps.home')
293 config.include('rhodecode.apps.journal')
293 config.include('rhodecode.apps.journal')
294 config.include('rhodecode.apps.repository')
294 config.include('rhodecode.apps.repository')
295 config.include('rhodecode.apps.repo_group')
295 config.include('rhodecode.apps.repo_group')
296 config.include('rhodecode.apps.user_group')
296 config.include('rhodecode.apps.user_group')
297 config.include('rhodecode.apps.search')
297 config.include('rhodecode.apps.search')
298 config.include('rhodecode.apps.user_profile')
298 config.include('rhodecode.apps.user_profile')
299 config.include('rhodecode.apps.user_group_profile')
299 config.include('rhodecode.apps.user_group_profile')
300 config.include('rhodecode.apps.my_account')
300 config.include('rhodecode.apps.my_account')
301 config.include('rhodecode.apps.svn_support')
301 config.include('rhodecode.apps.svn_support')
302 config.include('rhodecode.apps.ssh_support')
302 config.include('rhodecode.apps.ssh_support')
303 config.include('rhodecode.apps.gist')
303 config.include('rhodecode.apps.gist')
304 config.include('rhodecode.apps.debug_style')
304 config.include('rhodecode.apps.debug_style')
305 config.include('rhodecode.api')
305 config.include('rhodecode.api')
306
306
307 config.add_route('rhodecode_support', 'https://rhodecode.com/help/', static=True)
307 config.add_route('rhodecode_support', 'https://rhodecode.com/help/', static=True)
308 config.add_translation_dirs('rhodecode:i18n/')
308 config.add_translation_dirs('rhodecode:i18n/')
309 settings['default_locale_name'] = settings.get('lang', 'en')
309 settings['default_locale_name'] = settings.get('lang', 'en')
310
310
311 # Add subscribers.
311 # Add subscribers.
312 if load_all:
312 if load_all:
313 config.add_subscriber(inject_app_settings,
313 config.add_subscriber(inject_app_settings,
314 pyramid.events.ApplicationCreated)
314 pyramid.events.ApplicationCreated)
315 config.add_subscriber(scan_repositories_if_enabled,
315 config.add_subscriber(scan_repositories_if_enabled,
316 pyramid.events.ApplicationCreated)
316 pyramid.events.ApplicationCreated)
317 config.add_subscriber(write_metadata_if_needed,
317 config.add_subscriber(write_metadata_if_needed,
318 pyramid.events.ApplicationCreated)
318 pyramid.events.ApplicationCreated)
319 config.add_subscriber(write_js_routes_if_enabled,
319 config.add_subscriber(write_js_routes_if_enabled,
320 pyramid.events.ApplicationCreated)
320 pyramid.events.ApplicationCreated)
321
321
322 # request custom methods
322 # request custom methods
323 config.add_request_method(
323 config.add_request_method(
324 'rhodecode.lib.partial_renderer.get_partial_renderer',
324 'rhodecode.lib.partial_renderer.get_partial_renderer',
325 'get_partial_renderer')
325 'get_partial_renderer')
326
326
327 config.add_request_method(
327 config.add_request_method(
328 'rhodecode.lib.request_counter.get_request_counter',
328 'rhodecode.lib.request_counter.get_request_counter',
329 'request_count')
329 'request_count')
330
330
331 # Set the authorization policy.
331 # Set the authorization policy.
332 authz_policy = ACLAuthorizationPolicy()
332 authz_policy = ACLAuthorizationPolicy()
333 config.set_authorization_policy(authz_policy)
333 config.set_authorization_policy(authz_policy)
334
334
335 # Set the default renderer for HTML templates to mako.
335 # Set the default renderer for HTML templates to mako.
336 config.add_mako_renderer('.html')
336 config.add_mako_renderer('.html')
337
337
338 config.add_renderer(
338 config.add_renderer(
339 name='json_ext',
339 name='json_ext',
340 factory='rhodecode.lib.ext_json_renderer.pyramid_ext_json')
340 factory='rhodecode.lib.ext_json_renderer.pyramid_ext_json')
341
341
342 # include RhodeCode plugins
342 # include RhodeCode plugins
343 includes = aslist(settings.get('rhodecode.includes', []))
343 includes = aslist(settings.get('rhodecode.includes', []))
344 for inc in includes:
344 for inc in includes:
345 config.include(inc)
345 config.include(inc)
346
346
347 # custom not found view, if our pyramid app doesn't know how to handle
347 # custom not found view, if our pyramid app doesn't know how to handle
348 # the request pass it to potential VCS handling ap
348 # the request pass it to potential VCS handling ap
349 config.add_notfound_view(not_found_view)
349 config.add_notfound_view(not_found_view)
350 if not settings.get('debugtoolbar.enabled', False):
350 if not settings.get('debugtoolbar.enabled', False):
351 # disabled debugtoolbar handle all exceptions via the error_handlers
351 # disabled debugtoolbar handle all exceptions via the error_handlers
352 config.add_view(error_handler, context=Exception)
352 config.add_view(error_handler, context=Exception)
353
353
354 # all errors including 403/404/50X
354 # all errors including 403/404/50X
355 config.add_view(error_handler, context=HTTPError)
355 config.add_view(error_handler, context=HTTPError)
356
356
357
357
358 def wrap_app_in_wsgi_middlewares(pyramid_app, config):
358 def wrap_app_in_wsgi_middlewares(pyramid_app, config):
359 """
359 """
360 Apply outer WSGI middlewares around the application.
360 Apply outer WSGI middlewares around the application.
361 """
361 """
362 registry = config.registry
362 registry = config.registry
363 settings = registry.settings
363 settings = registry.settings
364
364
365 # enable https redirects based on HTTP_X_URL_SCHEME set by proxy
365 # enable https redirects based on HTTP_X_URL_SCHEME set by proxy
366 pyramid_app = HttpsFixup(pyramid_app, settings)
366 pyramid_app = HttpsFixup(pyramid_app, settings)
367
367
368 pyramid_app, _ae_client = wrap_in_appenlight_if_enabled(
368 pyramid_app, _ae_client = wrap_in_appenlight_if_enabled(
369 pyramid_app, settings)
369 pyramid_app, settings)
370 registry.ae_client = _ae_client
370 registry.ae_client = _ae_client
371
371
372 if settings['gzip_responses']:
372 if settings['gzip_responses']:
373 pyramid_app = make_gzip_middleware(
373 pyramid_app = make_gzip_middleware(
374 pyramid_app, settings, compress_level=1)
374 pyramid_app, settings, compress_level=1)
375
375
376 # this should be the outer most middleware in the wsgi stack since
376 # this should be the outer most middleware in the wsgi stack since
377 # middleware like Routes make database calls
377 # middleware like Routes make database calls
378 def pyramid_app_with_cleanup(environ, start_response):
378 def pyramid_app_with_cleanup(environ, start_response):
379 try:
379 try:
380 return pyramid_app(environ, start_response)
380 return pyramid_app(environ, start_response)
381 finally:
381 finally:
382 # Dispose current database session and rollback uncommitted
382 # Dispose current database session and rollback uncommitted
383 # transactions.
383 # transactions.
384 meta.Session.remove()
384 meta.Session.remove()
385
385
386 # In a single threaded mode server, on non sqlite db we should have
386 # In a single threaded mode server, on non sqlite db we should have
387 # '0 Current Checked out connections' at the end of a request,
387 # '0 Current Checked out connections' at the end of a request,
388 # if not, then something, somewhere is leaving a connection open
388 # if not, then something, somewhere is leaving a connection open
389 pool = meta.Base.metadata.bind.engine.pool
389 pool = meta.Base.metadata.bind.engine.pool
390 log.debug('sa pool status: %s', pool.status())
390 log.debug('sa pool status: %s', pool.status())
391 log.debug('Request processing finalized')
391 log.debug('Request processing finalized')
392
392
393 return pyramid_app_with_cleanup
393 return pyramid_app_with_cleanup
394
394
395
395
396 def sanitize_settings_and_apply_defaults(global_config, settings):
396 def sanitize_settings_and_apply_defaults(global_config, settings):
397 """
397 """
398 Applies settings defaults and does all type conversion.
398 Applies settings defaults and does all type conversion.
399
399
400 We would move all settings parsing and preparation into this place, so that
400 We would move all settings parsing and preparation into this place, so that
401 we have only one place left which deals with this part. The remaining parts
401 we have only one place left which deals with this part. The remaining parts
402 of the application would start to rely fully on well prepared settings.
402 of the application would start to rely fully on well prepared settings.
403
403
404 This piece would later be split up per topic to avoid a big fat monster
404 This piece would later be split up per topic to avoid a big fat monster
405 function.
405 function.
406 """
406 """
407
407
408 settings.setdefault('rhodecode.edition', 'Community Edition')
408 settings.setdefault('rhodecode.edition', 'Community Edition')
409
409
410 if 'mako.default_filters' not in settings:
410 if 'mako.default_filters' not in settings:
411 # set custom default filters if we don't have it defined
411 # set custom default filters if we don't have it defined
412 settings['mako.imports'] = 'from rhodecode.lib.base import h_filter'
412 settings['mako.imports'] = 'from rhodecode.lib.base import h_filter'
413 settings['mako.default_filters'] = 'h_filter'
413 settings['mako.default_filters'] = 'h_filter'
414
414
415 if 'mako.directories' not in settings:
415 if 'mako.directories' not in settings:
416 mako_directories = settings.setdefault('mako.directories', [
416 mako_directories = settings.setdefault('mako.directories', [
417 # Base templates of the original application
417 # Base templates of the original application
418 'rhodecode:templates',
418 'rhodecode:templates',
419 ])
419 ])
420 log.debug(
420 log.debug(
421 "Using the following Mako template directories: %s",
421 "Using the following Mako template directories: %s",
422 mako_directories)
422 mako_directories)
423
423
424 # NOTE(marcink): fix redis requirement for schema of connection since 3.X
424 # NOTE(marcink): fix redis requirement for schema of connection since 3.X
425 if 'beaker.session.type' in settings and settings['beaker.session.type'] == 'ext:redis':
425 if 'beaker.session.type' in settings and settings['beaker.session.type'] == 'ext:redis':
426 raw_url = settings['beaker.session.url']
426 raw_url = settings['beaker.session.url']
427 if not raw_url.startswith(('redis://', 'rediss://', 'unix://')):
427 if not raw_url.startswith(('redis://', 'rediss://', 'unix://')):
428 settings['beaker.session.url'] = 'redis://' + raw_url
428 settings['beaker.session.url'] = 'redis://' + raw_url
429
429
430 # Default includes, possible to change as a user
430 # Default includes, possible to change as a user
431 pyramid_includes = settings.setdefault('pyramid.includes', [])
431 pyramid_includes = settings.setdefault('pyramid.includes', [])
432 log.debug(
432 log.debug(
433 "Using the following pyramid.includes: %s",
433 "Using the following pyramid.includes: %s",
434 pyramid_includes)
434 pyramid_includes)
435
435
436 # TODO: johbo: Re-think this, usually the call to config.include
436 # TODO: johbo: Re-think this, usually the call to config.include
437 # should allow to pass in a prefix.
437 # should allow to pass in a prefix.
438 settings.setdefault('rhodecode.api.url', '/_admin/api')
438 settings.setdefault('rhodecode.api.url', '/_admin/api')
439 settings.setdefault('__file__', global_config.get('__file__'))
439 settings.setdefault('__file__', global_config.get('__file__'))
440
440
441 # Sanitize generic settings.
441 # Sanitize generic settings.
442 _list_setting(settings, 'default_encoding', 'UTF-8')
442 _list_setting(settings, 'default_encoding', 'UTF-8')
443 _bool_setting(settings, 'is_test', 'false')
443 _bool_setting(settings, 'is_test', 'false')
444 _bool_setting(settings, 'gzip_responses', 'false')
444 _bool_setting(settings, 'gzip_responses', 'false')
445
445
446 # Call split out functions that sanitize settings for each topic.
446 # Call split out functions that sanitize settings for each topic.
447 _sanitize_appenlight_settings(settings)
447 _sanitize_appenlight_settings(settings)
448 _sanitize_vcs_settings(settings)
448 _sanitize_vcs_settings(settings)
449 _sanitize_cache_settings(settings)
449 _sanitize_cache_settings(settings)
450
450
451 # configure instance id
451 # configure instance id
452 config_utils.set_instance_id(settings)
452 config_utils.set_instance_id(settings)
453
453
454 return settings
454 return settings
455
455
456
456
457 def enable_debug():
457 def enable_debug():
458 """
458 """
459 Helper to enable debug on running instance
459 Helper to enable debug on running instance
460 :return:
460 :return:
461 """
461 """
462 import tempfile
462 import tempfile
463 import textwrap
463 import textwrap
464 import logging.config
464 import logging.config
465
465
466 ini_template = textwrap.dedent("""
466 ini_template = textwrap.dedent("""
467 #####################################
467 #####################################
468 ### DEBUG LOGGING CONFIGURATION ####
468 ### DEBUG LOGGING CONFIGURATION ####
469 #####################################
469 #####################################
470 [loggers]
470 [loggers]
471 keys = root, sqlalchemy, beaker, celery, rhodecode, ssh_wrapper
471 keys = root, sqlalchemy, beaker, celery, rhodecode, ssh_wrapper
472
472
473 [handlers]
473 [handlers]
474 keys = console, console_sql
474 keys = console, console_sql
475
475
476 [formatters]
476 [formatters]
477 keys = generic, color_formatter, color_formatter_sql
477 keys = generic, color_formatter, color_formatter_sql
478
478
479 #############
479 #############
480 ## LOGGERS ##
480 ## LOGGERS ##
481 #############
481 #############
482 [logger_root]
482 [logger_root]
483 level = NOTSET
483 level = NOTSET
484 handlers = console
484 handlers = console
485
485
486 [logger_sqlalchemy]
486 [logger_sqlalchemy]
487 level = INFO
487 level = INFO
488 handlers = console_sql
488 handlers = console_sql
489 qualname = sqlalchemy.engine
489 qualname = sqlalchemy.engine
490 propagate = 0
490 propagate = 0
491
491
492 [logger_beaker]
492 [logger_beaker]
493 level = DEBUG
493 level = DEBUG
494 handlers =
494 handlers =
495 qualname = beaker.container
495 qualname = beaker.container
496 propagate = 1
496 propagate = 1
497
497
498 [logger_rhodecode]
498 [logger_rhodecode]
499 level = DEBUG
499 level = DEBUG
500 handlers =
500 handlers =
501 qualname = rhodecode
501 qualname = rhodecode
502 propagate = 1
502 propagate = 1
503
503
504 [logger_ssh_wrapper]
504 [logger_ssh_wrapper]
505 level = DEBUG
505 level = DEBUG
506 handlers =
506 handlers =
507 qualname = ssh_wrapper
507 qualname = ssh_wrapper
508 propagate = 1
508 propagate = 1
509
509
510 [logger_celery]
510 [logger_celery]
511 level = DEBUG
511 level = DEBUG
512 handlers =
512 handlers =
513 qualname = celery
513 qualname = celery
514
514
515
515
516 ##############
516 ##############
517 ## HANDLERS ##
517 ## HANDLERS ##
518 ##############
518 ##############
519
519
520 [handler_console]
520 [handler_console]
521 class = StreamHandler
521 class = StreamHandler
522 args = (sys.stderr, )
522 args = (sys.stderr, )
523 level = DEBUG
523 level = DEBUG
524 formatter = color_formatter
524 formatter = color_formatter
525
525
526 [handler_console_sql]
526 [handler_console_sql]
527 # "level = DEBUG" logs SQL queries and results.
527 # "level = DEBUG" logs SQL queries and results.
528 # "level = INFO" logs SQL queries.
528 # "level = INFO" logs SQL queries.
529 # "level = WARN" logs neither. (Recommended for production systems.)
529 # "level = WARN" logs neither. (Recommended for production systems.)
530 class = StreamHandler
530 class = StreamHandler
531 args = (sys.stderr, )
531 args = (sys.stderr, )
532 level = WARN
532 level = WARN
533 formatter = color_formatter_sql
533 formatter = color_formatter_sql
534
534
535 ################
535 ################
536 ## FORMATTERS ##
536 ## FORMATTERS ##
537 ################
537 ################
538
538
539 [formatter_generic]
539 [formatter_generic]
540 class = rhodecode.lib.logging_formatter.ExceptionAwareFormatter
540 class = rhodecode.lib.logging_formatter.ExceptionAwareFormatter
541 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s | %(req_id)s
541 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s | %(req_id)s
542 datefmt = %Y-%m-%d %H:%M:%S
542 datefmt = %Y-%m-%d %H:%M:%S
543
543
544 [formatter_color_formatter]
544 [formatter_color_formatter]
545 class = rhodecode.lib.logging_formatter.ColorRequestTrackingFormatter
545 class = rhodecode.lib.logging_formatter.ColorRequestTrackingFormatter
546 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s | %(req_id)s
546 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s | %(req_id)s
547 datefmt = %Y-%m-%d %H:%M:%S
547 datefmt = %Y-%m-%d %H:%M:%S
548
548
549 [formatter_color_formatter_sql]
549 [formatter_color_formatter_sql]
550 class = rhodecode.lib.logging_formatter.ColorFormatterSql
550 class = rhodecode.lib.logging_formatter.ColorFormatterSql
551 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s
551 format = %(asctime)s.%(msecs)03d [%(process)d] %(levelname)-5.5s [%(name)s] %(message)s
552 datefmt = %Y-%m-%d %H:%M:%S
552 datefmt = %Y-%m-%d %H:%M:%S
553 """)
553 """)
554
554
555 with tempfile.NamedTemporaryFile(prefix='rc_debug_logging_', suffix='.ini',
555 with tempfile.NamedTemporaryFile(prefix='rc_debug_logging_', suffix='.ini',
556 delete=False) as f:
556 delete=False) as f:
557 log.info('Saved Temporary DEBUG config at %s', f.name)
557 log.info('Saved Temporary DEBUG config at %s', f.name)
558 f.write(ini_template)
558 f.write(ini_template)
559
559
560 logging.config.fileConfig(f.name)
560 logging.config.fileConfig(f.name)
561 log.debug('DEBUG MODE ON')
561 log.debug('DEBUG MODE ON')
562 os.remove(f.name)
562 os.remove(f.name)
563
563
564
564
565 def _sanitize_appenlight_settings(settings):
565 def _sanitize_appenlight_settings(settings):
566 _bool_setting(settings, 'appenlight', 'false')
566 _bool_setting(settings, 'appenlight', 'false')
567
567
568
568
569 def _sanitize_vcs_settings(settings):
569 def _sanitize_vcs_settings(settings):
570 """
570 """
571 Applies settings defaults and does type conversion for all VCS related
571 Applies settings defaults and does type conversion for all VCS related
572 settings.
572 settings.
573 """
573 """
574 _string_setting(settings, 'vcs.svn.compatible_version', '')
574 _string_setting(settings, 'vcs.svn.compatible_version', '')
575 _string_setting(settings, 'vcs.hooks.protocol', 'http')
575 _string_setting(settings, 'vcs.hooks.protocol', 'http')
576 _string_setting(settings, 'vcs.hooks.host', '127.0.0.1')
576 _string_setting(settings, 'vcs.hooks.host', '127.0.0.1')
577 _string_setting(settings, 'vcs.scm_app_implementation', 'http')
577 _string_setting(settings, 'vcs.scm_app_implementation', 'http')
578 _string_setting(settings, 'vcs.server', '')
578 _string_setting(settings, 'vcs.server', '')
579 _string_setting(settings, 'vcs.server.log_level', 'debug')
580 _string_setting(settings, 'vcs.server.protocol', 'http')
579 _string_setting(settings, 'vcs.server.protocol', 'http')
581 _bool_setting(settings, 'startup.import_repos', 'false')
580 _bool_setting(settings, 'startup.import_repos', 'false')
582 _bool_setting(settings, 'vcs.hooks.direct_calls', 'false')
581 _bool_setting(settings, 'vcs.hooks.direct_calls', 'false')
583 _bool_setting(settings, 'vcs.server.enable', 'true')
582 _bool_setting(settings, 'vcs.server.enable', 'true')
584 _bool_setting(settings, 'vcs.start_server', 'false')
583 _bool_setting(settings, 'vcs.start_server', 'false')
585 _list_setting(settings, 'vcs.backends', 'hg, git, svn')
584 _list_setting(settings, 'vcs.backends', 'hg, git, svn')
586 _int_setting(settings, 'vcs.connection_timeout', 3600)
585 _int_setting(settings, 'vcs.connection_timeout', 3600)
587
586
588 # Support legacy values of vcs.scm_app_implementation. Legacy
587 # Support legacy values of vcs.scm_app_implementation. Legacy
589 # configurations may use 'rhodecode.lib.middleware.utils.scm_app_http', or
588 # configurations may use 'rhodecode.lib.middleware.utils.scm_app_http', or
590 # disabled since 4.13 'vcsserver.scm_app' which is now mapped to 'http'.
589 # disabled since 4.13 'vcsserver.scm_app' which is now mapped to 'http'.
591 scm_app_impl = settings['vcs.scm_app_implementation']
590 scm_app_impl = settings['vcs.scm_app_implementation']
592 if scm_app_impl in ['rhodecode.lib.middleware.utils.scm_app_http', 'vcsserver.scm_app']:
591 if scm_app_impl in ['rhodecode.lib.middleware.utils.scm_app_http', 'vcsserver.scm_app']:
593 settings['vcs.scm_app_implementation'] = 'http'
592 settings['vcs.scm_app_implementation'] = 'http'
594
593
595
594
596 def _sanitize_cache_settings(settings):
595 def _sanitize_cache_settings(settings):
597 temp_store = tempfile.gettempdir()
596 temp_store = tempfile.gettempdir()
598 default_cache_dir = os.path.join(temp_store, 'rc_cache')
597 default_cache_dir = os.path.join(temp_store, 'rc_cache')
599
598
600 # save default, cache dir, and use it for all backends later.
599 # save default, cache dir, and use it for all backends later.
601 default_cache_dir = _string_setting(
600 default_cache_dir = _string_setting(
602 settings,
601 settings,
603 'cache_dir',
602 'cache_dir',
604 default_cache_dir, lower=False, default_when_empty=True)
603 default_cache_dir, lower=False, default_when_empty=True)
605
604
606 # ensure we have our dir created
605 # ensure we have our dir created
607 if not os.path.isdir(default_cache_dir):
606 if not os.path.isdir(default_cache_dir):
608 os.makedirs(default_cache_dir, mode=0o755)
607 os.makedirs(default_cache_dir, mode=0o755)
609
608
610 # exception store cache
609 # exception store cache
611 _string_setting(
610 _string_setting(
612 settings,
611 settings,
613 'exception_tracker.store_path',
612 'exception_tracker.store_path',
614 temp_store, lower=False, default_when_empty=True)
613 temp_store, lower=False, default_when_empty=True)
615
614
616 # cache_perms
615 # cache_perms
617 _string_setting(
616 _string_setting(
618 settings,
617 settings,
619 'rc_cache.cache_perms.backend',
618 'rc_cache.cache_perms.backend',
620 'dogpile.cache.rc.file_namespace', lower=False)
619 'dogpile.cache.rc.file_namespace', lower=False)
621 _int_setting(
620 _int_setting(
622 settings,
621 settings,
623 'rc_cache.cache_perms.expiration_time',
622 'rc_cache.cache_perms.expiration_time',
624 60)
623 60)
625 _string_setting(
624 _string_setting(
626 settings,
625 settings,
627 'rc_cache.cache_perms.arguments.filename',
626 'rc_cache.cache_perms.arguments.filename',
628 os.path.join(default_cache_dir, 'rc_cache_1'), lower=False)
627 os.path.join(default_cache_dir, 'rc_cache_1'), lower=False)
629
628
630 # cache_repo
629 # cache_repo
631 _string_setting(
630 _string_setting(
632 settings,
631 settings,
633 'rc_cache.cache_repo.backend',
632 'rc_cache.cache_repo.backend',
634 'dogpile.cache.rc.file_namespace', lower=False)
633 'dogpile.cache.rc.file_namespace', lower=False)
635 _int_setting(
634 _int_setting(
636 settings,
635 settings,
637 'rc_cache.cache_repo.expiration_time',
636 'rc_cache.cache_repo.expiration_time',
638 60)
637 60)
639 _string_setting(
638 _string_setting(
640 settings,
639 settings,
641 'rc_cache.cache_repo.arguments.filename',
640 'rc_cache.cache_repo.arguments.filename',
642 os.path.join(default_cache_dir, 'rc_cache_2'), lower=False)
641 os.path.join(default_cache_dir, 'rc_cache_2'), lower=False)
643
642
644 # cache_license
643 # cache_license
645 _string_setting(
644 _string_setting(
646 settings,
645 settings,
647 'rc_cache.cache_license.backend',
646 'rc_cache.cache_license.backend',
648 'dogpile.cache.rc.file_namespace', lower=False)
647 'dogpile.cache.rc.file_namespace', lower=False)
649 _int_setting(
648 _int_setting(
650 settings,
649 settings,
651 'rc_cache.cache_license.expiration_time',
650 'rc_cache.cache_license.expiration_time',
652 5*60)
651 5*60)
653 _string_setting(
652 _string_setting(
654 settings,
653 settings,
655 'rc_cache.cache_license.arguments.filename',
654 'rc_cache.cache_license.arguments.filename',
656 os.path.join(default_cache_dir, 'rc_cache_3'), lower=False)
655 os.path.join(default_cache_dir, 'rc_cache_3'), lower=False)
657
656
658 # cache_repo_longterm memory, 96H
657 # cache_repo_longterm memory, 96H
659 _string_setting(
658 _string_setting(
660 settings,
659 settings,
661 'rc_cache.cache_repo_longterm.backend',
660 'rc_cache.cache_repo_longterm.backend',
662 'dogpile.cache.rc.memory_lru', lower=False)
661 'dogpile.cache.rc.memory_lru', lower=False)
663 _int_setting(
662 _int_setting(
664 settings,
663 settings,
665 'rc_cache.cache_repo_longterm.expiration_time',
664 'rc_cache.cache_repo_longterm.expiration_time',
666 345600)
665 345600)
667 _int_setting(
666 _int_setting(
668 settings,
667 settings,
669 'rc_cache.cache_repo_longterm.max_size',
668 'rc_cache.cache_repo_longterm.max_size',
670 10000)
669 10000)
671
670
672 # sql_cache_short
671 # sql_cache_short
673 _string_setting(
672 _string_setting(
674 settings,
673 settings,
675 'rc_cache.sql_cache_short.backend',
674 'rc_cache.sql_cache_short.backend',
676 'dogpile.cache.rc.memory_lru', lower=False)
675 'dogpile.cache.rc.memory_lru', lower=False)
677 _int_setting(
676 _int_setting(
678 settings,
677 settings,
679 'rc_cache.sql_cache_short.expiration_time',
678 'rc_cache.sql_cache_short.expiration_time',
680 30)
679 30)
681 _int_setting(
680 _int_setting(
682 settings,
681 settings,
683 'rc_cache.sql_cache_short.max_size',
682 'rc_cache.sql_cache_short.max_size',
684 10000)
683 10000)
685
684
686
685
687 def _int_setting(settings, name, default):
686 def _int_setting(settings, name, default):
688 settings[name] = int(settings.get(name, default))
687 settings[name] = int(settings.get(name, default))
689 return settings[name]
688 return settings[name]
690
689
691
690
692 def _bool_setting(settings, name, default):
691 def _bool_setting(settings, name, default):
693 input_val = settings.get(name, default)
692 input_val = settings.get(name, default)
694 if isinstance(input_val, unicode):
693 if isinstance(input_val, unicode):
695 input_val = input_val.encode('utf8')
694 input_val = input_val.encode('utf8')
696 settings[name] = asbool(input_val)
695 settings[name] = asbool(input_val)
697 return settings[name]
696 return settings[name]
698
697
699
698
700 def _list_setting(settings, name, default):
699 def _list_setting(settings, name, default):
701 raw_value = settings.get(name, default)
700 raw_value = settings.get(name, default)
702
701
703 old_separator = ','
702 old_separator = ','
704 if old_separator in raw_value:
703 if old_separator in raw_value:
705 # If we get a comma separated list, pass it to our own function.
704 # If we get a comma separated list, pass it to our own function.
706 settings[name] = rhodecode_aslist(raw_value, sep=old_separator)
705 settings[name] = rhodecode_aslist(raw_value, sep=old_separator)
707 else:
706 else:
708 # Otherwise we assume it uses pyramids space/newline separation.
707 # Otherwise we assume it uses pyramids space/newline separation.
709 settings[name] = aslist(raw_value)
708 settings[name] = aslist(raw_value)
710 return settings[name]
709 return settings[name]
711
710
712
711
713 def _string_setting(settings, name, default, lower=True, default_when_empty=False):
712 def _string_setting(settings, name, default, lower=True, default_when_empty=False):
714 value = settings.get(name, default)
713 value = settings.get(name, default)
715
714
716 if default_when_empty and not value:
715 if default_when_empty and not value:
717 # use default value when value is empty
716 # use default value when value is empty
718 value = default
717 value = default
719
718
720 if lower:
719 if lower:
721 value = value.lower()
720 value = value.lower()
722 settings[name] = value
721 settings[name] = value
723 return settings[name]
722 return settings[name]
724
723
725
724
726 def _substitute_values(mapping, substitutions):
725 def _substitute_values(mapping, substitutions):
727 result = {}
726 result = {}
728
727
729 try:
728 try:
730 for key, value in mapping.items():
729 for key, value in mapping.items():
731 # initialize without substitution first
730 # initialize without substitution first
732 result[key] = value
731 result[key] = value
733
732
734 # Note: Cannot use regular replacements, since they would clash
733 # Note: Cannot use regular replacements, since they would clash
735 # with the implementation of ConfigParser. Using "format" instead.
734 # with the implementation of ConfigParser. Using "format" instead.
736 try:
735 try:
737 result[key] = value.format(**substitutions)
736 result[key] = value.format(**substitutions)
738 except KeyError as e:
737 except KeyError as e:
739 env_var = '{}'.format(e.args[0])
738 env_var = '{}'.format(e.args[0])
740
739
741 msg = 'Failed to substitute: `{key}={{{var}}}` with environment entry. ' \
740 msg = 'Failed to substitute: `{key}={{{var}}}` with environment entry. ' \
742 'Make sure your environment has {var} set, or remove this ' \
741 'Make sure your environment has {var} set, or remove this ' \
743 'variable from config file'.format(key=key, var=env_var)
742 'variable from config file'.format(key=key, var=env_var)
744
743
745 if env_var.startswith('ENV_'):
744 if env_var.startswith('ENV_'):
746 raise ValueError(msg)
745 raise ValueError(msg)
747 else:
746 else:
748 log.warning(msg)
747 log.warning(msg)
749
748
750 except ValueError as e:
749 except ValueError as e:
751 log.warning('Failed to substitute ENV variable: %s', e)
750 log.warning('Failed to substitute ENV variable: %s', e)
752 result = mapping
751 result = mapping
753
752
754 return result
753 return result
@@ -1,204 +1,203 b''
1 # -*- coding: utf-8 -*-
1 # -*- coding: utf-8 -*-
2
2
3 # Copyright (C) 2016-2019 RhodeCode GmbH
3 # Copyright (C) 2016-2019 RhodeCode GmbH
4 #
4 #
5 # This program is free software: you can redistribute it and/or modify
5 # This program is free software: you can redistribute it and/or modify
6 # it under the terms of the GNU Affero General Public License, version 3
6 # it under the terms of the GNU Affero General Public License, version 3
7 # (only), as published by the Free Software Foundation.
7 # (only), as published by the Free Software Foundation.
8 #
8 #
9 # This program is distributed in the hope that it will be useful,
9 # This program is distributed in the hope that it will be useful,
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
10 # but WITHOUT ANY WARRANTY; without even the implied warranty of
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
11 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 # GNU General Public License for more details.
12 # GNU General Public License for more details.
13 #
13 #
14 # You should have received a copy of the GNU Affero General Public License
14 # You should have received a copy of the GNU Affero General Public License
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
15 # along with this program. If not, see <http://www.gnu.org/licenses/>.
16 #
16 #
17 # This program is dual-licensed. If you wish to learn more about the
17 # This program is dual-licensed. If you wish to learn more about the
18 # RhodeCode Enterprise Edition, including its added features, Support services,
18 # RhodeCode Enterprise Edition, including its added features, Support services,
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
19 # and proprietary license terms, please see https://rhodecode.com/licenses/
20
20
21
21
22 import pytest
22 import pytest
23
23
24 from rhodecode.tests import no_newline_id_generator
24 from rhodecode.tests import no_newline_id_generator
25 from rhodecode.config.middleware import (
25 from rhodecode.config.middleware import (
26 _sanitize_vcs_settings, _bool_setting, _string_setting, _list_setting,
26 _sanitize_vcs_settings, _bool_setting, _string_setting, _list_setting,
27 _int_setting)
27 _int_setting)
28
28
29
29
30 class TestHelperFunctions(object):
30 class TestHelperFunctions(object):
31 @pytest.mark.parametrize('raw, expected', [
31 @pytest.mark.parametrize('raw, expected', [
32 ('true', True), (u'true', True),
32 ('true', True), (u'true', True),
33 ('yes', True), (u'yes', True),
33 ('yes', True), (u'yes', True),
34 ('on', True), (u'on', True),
34 ('on', True), (u'on', True),
35 ('false', False), (u'false', False),
35 ('false', False), (u'false', False),
36 ('no', False), (u'no', False),
36 ('no', False), (u'no', False),
37 ('off', False), (u'off', False),
37 ('off', False), (u'off', False),
38 ('invalid-bool-value', False),
38 ('invalid-bool-value', False),
39 ('invalid-∫øø@-√Γ₯@¨€', False),
39 ('invalid-∫øø@-√Γ₯@¨€', False),
40 (u'invalid-∫øø@-√Γ₯@¨€', False),
40 (u'invalid-∫øø@-√Γ₯@¨€', False),
41 ])
41 ])
42 def test_bool_setting_helper(self, raw, expected):
42 def test_bool_setting_helper(self, raw, expected):
43 key = 'dummy-key'
43 key = 'dummy-key'
44 settings = {key: raw}
44 settings = {key: raw}
45 _bool_setting(settings, key, None)
45 _bool_setting(settings, key, None)
46 assert settings[key] is expected
46 assert settings[key] is expected
47
47
48 @pytest.mark.parametrize('raw, expected', [
48 @pytest.mark.parametrize('raw, expected', [
49 ('', ''),
49 ('', ''),
50 ('test-string', 'test-string'),
50 ('test-string', 'test-string'),
51 ('CaSe-TeSt', 'case-test'),
51 ('CaSe-TeSt', 'case-test'),
52 ('test-string-烩€', 'test-string-烩€'),
52 ('test-string-烩€', 'test-string-烩€'),
53 (u'test-string-烩€', u'test-string-烩€'),
53 (u'test-string-烩€', u'test-string-烩€'),
54 ])
54 ])
55 def test_string_setting_helper(self, raw, expected):
55 def test_string_setting_helper(self, raw, expected):
56 key = 'dummy-key'
56 key = 'dummy-key'
57 settings = {key: raw}
57 settings = {key: raw}
58 _string_setting(settings, key, None)
58 _string_setting(settings, key, None)
59 assert settings[key] == expected
59 assert settings[key] == expected
60
60
61 @pytest.mark.parametrize('raw, expected', [
61 @pytest.mark.parametrize('raw, expected', [
62 ('', []),
62 ('', []),
63 ('test', ['test']),
63 ('test', ['test']),
64 ('CaSe-TeSt', ['CaSe-TeSt']),
64 ('CaSe-TeSt', ['CaSe-TeSt']),
65 ('test-string-烩€', ['test-string-烩€']),
65 ('test-string-烩€', ['test-string-烩€']),
66 (u'test-string-烩€', [u'test-string-烩€']),
66 (u'test-string-烩€', [u'test-string-烩€']),
67 ('hg git svn', ['hg', 'git', 'svn']),
67 ('hg git svn', ['hg', 'git', 'svn']),
68 ('hg,git,svn', ['hg', 'git', 'svn']),
68 ('hg,git,svn', ['hg', 'git', 'svn']),
69 ('hg, git, svn', ['hg', 'git', 'svn']),
69 ('hg, git, svn', ['hg', 'git', 'svn']),
70 ('hg\ngit\nsvn', ['hg', 'git', 'svn']),
70 ('hg\ngit\nsvn', ['hg', 'git', 'svn']),
71 (' hg\n git\n svn ', ['hg', 'git', 'svn']),
71 (' hg\n git\n svn ', ['hg', 'git', 'svn']),
72 (', hg , git , svn , ', ['', 'hg', 'git', 'svn', '']),
72 (', hg , git , svn , ', ['', 'hg', 'git', 'svn', '']),
73 ('cheese,free node,other', ['cheese', 'free node', 'other']),
73 ('cheese,free node,other', ['cheese', 'free node', 'other']),
74 ], ids=no_newline_id_generator)
74 ], ids=no_newline_id_generator)
75 def test_list_setting_helper(self, raw, expected):
75 def test_list_setting_helper(self, raw, expected):
76 key = 'dummy-key'
76 key = 'dummy-key'
77 settings = {key: raw}
77 settings = {key: raw}
78 _list_setting(settings, key, None)
78 _list_setting(settings, key, None)
79 assert settings[key] == expected
79 assert settings[key] == expected
80
80
81 @pytest.mark.parametrize('raw, expected', [
81 @pytest.mark.parametrize('raw, expected', [
82 ('0', 0),
82 ('0', 0),
83 ('-0', 0),
83 ('-0', 0),
84 ('12345', 12345),
84 ('12345', 12345),
85 ('-12345', -12345),
85 ('-12345', -12345),
86 (u'-12345', -12345),
86 (u'-12345', -12345),
87 ])
87 ])
88 def test_int_setting_helper(self, raw, expected):
88 def test_int_setting_helper(self, raw, expected):
89 key = 'dummy-key'
89 key = 'dummy-key'
90 settings = {key: raw}
90 settings = {key: raw}
91 _int_setting(settings, key, None)
91 _int_setting(settings, key, None)
92 assert settings[key] == expected
92 assert settings[key] == expected
93
93
94 @pytest.mark.parametrize('raw', [
94 @pytest.mark.parametrize('raw', [
95 ('0xff'),
95 ('0xff'),
96 (''),
96 (''),
97 ('invalid-int'),
97 ('invalid-int'),
98 ('invalid-⁄~†'),
98 ('invalid-⁄~†'),
99 (u'invalid-⁄~†'),
99 (u'invalid-⁄~†'),
100 ])
100 ])
101 def test_int_setting_helper_invalid_input(self, raw):
101 def test_int_setting_helper_invalid_input(self, raw):
102 key = 'dummy-key'
102 key = 'dummy-key'
103 settings = {key: raw}
103 settings = {key: raw}
104 with pytest.raises(Exception):
104 with pytest.raises(Exception):
105 _int_setting(settings, key, None)
105 _int_setting(settings, key, None)
106
106
107
107
108 class TestSanitizeVcsSettings(object):
108 class TestSanitizeVcsSettings(object):
109 _bool_settings = [
109 _bool_settings = [
110 ('vcs.hooks.direct_calls', False),
110 ('vcs.hooks.direct_calls', False),
111 ('vcs.server.enable', True),
111 ('vcs.server.enable', True),
112 ('vcs.start_server', False),
112 ('vcs.start_server', False),
113 ('startup.import_repos', False),
113 ('startup.import_repos', False),
114 ]
114 ]
115
115
116 _string_settings = [
116 _string_settings = [
117 ('vcs.svn.compatible_version', ''),
117 ('vcs.svn.compatible_version', ''),
118 ('vcs.hooks.protocol', 'http'),
118 ('vcs.hooks.protocol', 'http'),
119 ('vcs.hooks.host', '127.0.0.1'),
119 ('vcs.hooks.host', '127.0.0.1'),
120 ('vcs.scm_app_implementation', 'http'),
120 ('vcs.scm_app_implementation', 'http'),
121 ('vcs.server', ''),
121 ('vcs.server', ''),
122 ('vcs.server.log_level', 'debug'),
123 ('vcs.server.protocol', 'http'),
122 ('vcs.server.protocol', 'http'),
124 ]
123 ]
125
124
126 _list_settings = [
125 _list_settings = [
127 ('vcs.backends', 'hg git'),
126 ('vcs.backends', 'hg git'),
128 ]
127 ]
129
128
130 @pytest.mark.parametrize('key, default', _list_settings)
129 @pytest.mark.parametrize('key, default', _list_settings)
131 def test_list_setting_spacesep_list(self, key, default):
130 def test_list_setting_spacesep_list(self, key, default):
132 test_list = ['test', 'list', 'values', 'for', key]
131 test_list = ['test', 'list', 'values', 'for', key]
133 input_value = ' '.join(test_list)
132 input_value = ' '.join(test_list)
134 settings = {key: input_value}
133 settings = {key: input_value}
135 _sanitize_vcs_settings(settings)
134 _sanitize_vcs_settings(settings)
136 assert settings[key] == test_list
135 assert settings[key] == test_list
137
136
138 @pytest.mark.parametrize('key, default', _list_settings)
137 @pytest.mark.parametrize('key, default', _list_settings)
139 def test_list_setting_newlinesep_list(self, key, default):
138 def test_list_setting_newlinesep_list(self, key, default):
140 test_list = ['test', 'list', 'values', 'for', key]
139 test_list = ['test', 'list', 'values', 'for', key]
141 input_value = '\n'.join(test_list)
140 input_value = '\n'.join(test_list)
142 settings = {key: input_value}
141 settings = {key: input_value}
143 _sanitize_vcs_settings(settings)
142 _sanitize_vcs_settings(settings)
144 assert settings[key] == test_list
143 assert settings[key] == test_list
145
144
146 @pytest.mark.parametrize('key, default', _list_settings)
145 @pytest.mark.parametrize('key, default', _list_settings)
147 def test_list_setting_commasep_list(self, key, default):
146 def test_list_setting_commasep_list(self, key, default):
148 test_list = ['test', 'list', 'values', 'for', key]
147 test_list = ['test', 'list', 'values', 'for', key]
149 input_value = ','.join(test_list)
148 input_value = ','.join(test_list)
150 settings = {key: input_value}
149 settings = {key: input_value}
151 _sanitize_vcs_settings(settings)
150 _sanitize_vcs_settings(settings)
152 assert settings[key] == test_list
151 assert settings[key] == test_list
153
152
154 @pytest.mark.parametrize('key, default', _list_settings)
153 @pytest.mark.parametrize('key, default', _list_settings)
155 def test_list_setting_comma_and_space_sep_list(self, key, default):
154 def test_list_setting_comma_and_space_sep_list(self, key, default):
156 test_list = ['test', 'list', 'values', 'for', key]
155 test_list = ['test', 'list', 'values', 'for', key]
157 input_value = ', '.join(test_list)
156 input_value = ', '.join(test_list)
158 settings = {key: input_value}
157 settings = {key: input_value}
159 _sanitize_vcs_settings(settings)
158 _sanitize_vcs_settings(settings)
160 assert settings[key] == test_list
159 assert settings[key] == test_list
161
160
162 @pytest.mark.parametrize('key, default', _string_settings)
161 @pytest.mark.parametrize('key, default', _string_settings)
163 def test_string_setting_string(self, key, default):
162 def test_string_setting_string(self, key, default):
164 test_value = 'test-string-for-{}'.format(key)
163 test_value = 'test-string-for-{}'.format(key)
165 settings = {key: test_value}
164 settings = {key: test_value}
166 _sanitize_vcs_settings(settings)
165 _sanitize_vcs_settings(settings)
167 assert settings[key] == test_value
166 assert settings[key] == test_value
168
167
169 @pytest.mark.parametrize('key, default', _string_settings)
168 @pytest.mark.parametrize('key, default', _string_settings)
170 def test_string_setting_default(self, key, default):
169 def test_string_setting_default(self, key, default):
171 settings = {}
170 settings = {}
172 _sanitize_vcs_settings(settings)
171 _sanitize_vcs_settings(settings)
173 assert settings[key] == default
172 assert settings[key] == default
174
173
175 @pytest.mark.parametrize('key, default', _string_settings)
174 @pytest.mark.parametrize('key, default', _string_settings)
176 def test_string_setting_lowercase(self, key, default):
175 def test_string_setting_lowercase(self, key, default):
177 test_value = 'Test-String-For-{}'.format(key)
176 test_value = 'Test-String-For-{}'.format(key)
178 settings = {key: test_value}
177 settings = {key: test_value}
179 _sanitize_vcs_settings(settings)
178 _sanitize_vcs_settings(settings)
180 assert settings[key] == test_value.lower()
179 assert settings[key] == test_value.lower()
181
180
182 @pytest.mark.parametrize('key, default', _bool_settings)
181 @pytest.mark.parametrize('key, default', _bool_settings)
183 def test_bool_setting_true(self, key, default):
182 def test_bool_setting_true(self, key, default):
184 settings = {key: 'true'}
183 settings = {key: 'true'}
185 _sanitize_vcs_settings(settings)
184 _sanitize_vcs_settings(settings)
186 assert settings[key] is True
185 assert settings[key] is True
187
186
188 @pytest.mark.parametrize('key, default', _bool_settings)
187 @pytest.mark.parametrize('key, default', _bool_settings)
189 def test_bool_setting_false(self, key, default):
188 def test_bool_setting_false(self, key, default):
190 settings = {key: 'false'}
189 settings = {key: 'false'}
191 _sanitize_vcs_settings(settings)
190 _sanitize_vcs_settings(settings)
192 assert settings[key] is False
191 assert settings[key] is False
193
192
194 @pytest.mark.parametrize('key, default', _bool_settings)
193 @pytest.mark.parametrize('key, default', _bool_settings)
195 def test_bool_setting_invalid_string(self, key, default):
194 def test_bool_setting_invalid_string(self, key, default):
196 settings = {key: 'no-bool-val-string'}
195 settings = {key: 'no-bool-val-string'}
197 _sanitize_vcs_settings(settings)
196 _sanitize_vcs_settings(settings)
198 assert settings[key] is False
197 assert settings[key] is False
199
198
200 @pytest.mark.parametrize('key, default', _bool_settings)
199 @pytest.mark.parametrize('key, default', _bool_settings)
201 def test_bool_setting_default(self, key, default):
200 def test_bool_setting_default(self, key, default):
202 settings = {}
201 settings = {}
203 _sanitize_vcs_settings(settings)
202 _sanitize_vcs_settings(settings)
204 assert settings[key] is default
203 assert settings[key] is default
@@ -1,664 +1,664 b''
1
1
2
2
3 ################################################################################
3 ################################################################################
4 ## RHODECODE COMMUNITY EDITION CONFIGURATION ##
4 ## RHODECODE COMMUNITY EDITION CONFIGURATION ##
5 # The %(here)s variable will be replaced with the parent directory of this file#
5 # The %(here)s variable will be replaced with the parent directory of this file#
6 ################################################################################
6 ################################################################################
7
7
8 [DEFAULT]
8 [DEFAULT]
9 debug = true
9 debug = true
10
10
11 ################################################################################
11 ################################################################################
12 ## EMAIL CONFIGURATION ##
12 ## EMAIL CONFIGURATION ##
13 ## Uncomment and replace with the email address which should receive ##
13 ## Uncomment and replace with the email address which should receive ##
14 ## any error reports after an application crash ##
14 ## any error reports after an application crash ##
15 ## Additionally these settings will be used by the RhodeCode mailing system ##
15 ## Additionally these settings will be used by the RhodeCode mailing system ##
16 ################################################################################
16 ################################################################################
17
17
18 ## prefix all emails subjects with given prefix, helps filtering out emails
18 ## prefix all emails subjects with given prefix, helps filtering out emails
19 #email_prefix = [RhodeCode]
19 #email_prefix = [RhodeCode]
20
20
21 ## email FROM address all mails will be sent
21 ## email FROM address all mails will be sent
22 #app_email_from = rhodecode-noreply@localhost
22 #app_email_from = rhodecode-noreply@localhost
23
23
24 ## Uncomment and replace with the address which should receive any error report
24 ## Uncomment and replace with the address which should receive any error report
25 ## note: using appenlight for error handling doesn't need this to be uncommented
25 ## note: using appenlight for error handling doesn't need this to be uncommented
26 #email_to = admin@localhost
26 #email_to = admin@localhost
27
27
28 #smtp_server = mail.server.com
28 #smtp_server = mail.server.com
29 #smtp_username =
29 #smtp_username =
30 #smtp_password =
30 #smtp_password =
31 #smtp_port =
31 #smtp_port =
32 #smtp_use_tls = false
32 #smtp_use_tls = false
33 #smtp_use_ssl = true
33 #smtp_use_ssl = true
34
34
35 [server:main]
35 [server:main]
36 ## COMMON ##
36 ## COMMON ##
37 host = 0.0.0.0
37 host = 0.0.0.0
38 port = 5000
38 port = 5000
39
39
40 ##########################
40 ##########################
41 ## GUNICORN WSGI SERVER ##
41 ## GUNICORN WSGI SERVER ##
42 ##########################
42 ##########################
43 ## run with gunicorn --log-config rhodecode.ini --paste rhodecode.ini
43 ## run with gunicorn --log-config rhodecode.ini --paste rhodecode.ini
44
44
45 use = egg:gunicorn#main
45 use = egg:gunicorn#main
46 ## Sets the number of process workers. You must set `instance_id = *`
46 ## Sets the number of process workers. You must set `instance_id = *`
47 ## when this option is set to more than one worker, recommended
47 ## when this option is set to more than one worker, recommended
48 ## value is (2 * NUMBER_OF_CPUS + 1), eg 2CPU = 5 workers
48 ## value is (2 * NUMBER_OF_CPUS + 1), eg 2CPU = 5 workers
49 ## The `instance_id = *` must be set in the [app:main] section below
49 ## The `instance_id = *` must be set in the [app:main] section below
50 #workers = 2
50 #workers = 2
51 ## number of threads for each of the worker, must be set to 1 for gevent
51 ## number of threads for each of the worker, must be set to 1 for gevent
52 ## generally recommened to be at 1
52 ## generally recommened to be at 1
53 #threads = 1
53 #threads = 1
54 ## process name
54 ## process name
55 #proc_name = rhodecode
55 #proc_name = rhodecode
56 ## type of worker class, one of sync, gevent
56 ## type of worker class, one of sync, gevent
57 ## recommended for bigger setup is using of of other than sync one
57 ## recommended for bigger setup is using of of other than sync one
58 #worker_class = sync
58 #worker_class = sync
59 ## The maximum number of simultaneous clients. Valid only for Gevent
59 ## The maximum number of simultaneous clients. Valid only for Gevent
60 #worker_connections = 10
60 #worker_connections = 10
61 ## max number of requests that worker will handle before being gracefully
61 ## max number of requests that worker will handle before being gracefully
62 ## restarted, could prevent memory leaks
62 ## restarted, could prevent memory leaks
63 #max_requests = 1000
63 #max_requests = 1000
64 #max_requests_jitter = 30
64 #max_requests_jitter = 30
65 ## amount of time a worker can spend with handling a request before it
65 ## amount of time a worker can spend with handling a request before it
66 ## gets killed and restarted. Set to 6hrs
66 ## gets killed and restarted. Set to 6hrs
67 #timeout = 21600
67 #timeout = 21600
68
68
69 ## prefix middleware for RhodeCode.
69 ## prefix middleware for RhodeCode.
70 ## recommended when using proxy setup.
70 ## recommended when using proxy setup.
71 ## allows to set RhodeCode under a prefix in server.
71 ## allows to set RhodeCode under a prefix in server.
72 ## eg https://server.com/custom_prefix. Enable `filter-with =` option below as well.
72 ## eg https://server.com/custom_prefix. Enable `filter-with =` option below as well.
73 ## And set your prefix like: `prefix = /custom_prefix`
73 ## And set your prefix like: `prefix = /custom_prefix`
74 ## be sure to also set beaker.session.cookie_path = /custom_prefix if you need
74 ## be sure to also set beaker.session.cookie_path = /custom_prefix if you need
75 ## to make your cookies only work on prefix url
75 ## to make your cookies only work on prefix url
76 [filter:proxy-prefix]
76 [filter:proxy-prefix]
77 use = egg:PasteDeploy#prefix
77 use = egg:PasteDeploy#prefix
78 prefix = /
78 prefix = /
79
79
80 [app:main]
80 [app:main]
81 is_test = True
81 is_test = True
82 use = egg:rhodecode-enterprise-ce
82 use = egg:rhodecode-enterprise-ce
83
83
84 ## enable proxy prefix middleware, defined above
84 ## enable proxy prefix middleware, defined above
85 #filter-with = proxy-prefix
85 #filter-with = proxy-prefix
86
86
87
87
88 ## RHODECODE PLUGINS ##
88 ## RHODECODE PLUGINS ##
89 rhodecode.includes = rhodecode.api
89 rhodecode.includes = rhodecode.api
90
90
91 # api prefix url
91 # api prefix url
92 rhodecode.api.url = /_admin/api
92 rhodecode.api.url = /_admin/api
93
93
94
94
95 ## END RHODECODE PLUGINS ##
95 ## END RHODECODE PLUGINS ##
96
96
97 ## encryption key used to encrypt social plugin tokens,
97 ## encryption key used to encrypt social plugin tokens,
98 ## remote_urls with credentials etc, if not set it defaults to
98 ## remote_urls with credentials etc, if not set it defaults to
99 ## `beaker.session.secret`
99 ## `beaker.session.secret`
100 #rhodecode.encrypted_values.secret =
100 #rhodecode.encrypted_values.secret =
101
101
102 ## decryption strict mode (enabled by default). It controls if decryption raises
102 ## decryption strict mode (enabled by default). It controls if decryption raises
103 ## `SignatureVerificationError` in case of wrong key, or damaged encryption data.
103 ## `SignatureVerificationError` in case of wrong key, or damaged encryption data.
104 #rhodecode.encrypted_values.strict = false
104 #rhodecode.encrypted_values.strict = false
105
105
106 ## return gzipped responses from Rhodecode (static files/application)
106 ## return gzipped responses from Rhodecode (static files/application)
107 gzip_responses = false
107 gzip_responses = false
108
108
109 ## autogenerate javascript routes file on startup
109 ## autogenerate javascript routes file on startup
110 generate_js_files = false
110 generate_js_files = false
111
111
112 ## Optional Languages
112 ## Optional Languages
113 ## en(default), be, de, es, fr, it, ja, pl, pt, ru, zh
113 ## en(default), be, de, es, fr, it, ja, pl, pt, ru, zh
114 lang = en
114 lang = en
115
115
116 ## perform a full repository scan on each server start, this should be
116 ## perform a full repository scan on each server start, this should be
117 ## set to false after first startup, to allow faster server restarts.
117 ## set to false after first startup, to allow faster server restarts.
118 startup.import_repos = true
118 startup.import_repos = true
119
119
120 ## Uncomment and set this path to use archive download cache.
120 ## Uncomment and set this path to use archive download cache.
121 ## Once enabled, generated archives will be cached at this location
121 ## Once enabled, generated archives will be cached at this location
122 ## and served from the cache during subsequent requests for the same archive of
122 ## and served from the cache during subsequent requests for the same archive of
123 ## the repository.
123 ## the repository.
124 #archive_cache_dir = /tmp/tarballcache
124 #archive_cache_dir = /tmp/tarballcache
125
125
126 ## URL at which the application is running. This is used for bootstraping
126 ## URL at which the application is running. This is used for bootstraping
127 ## requests in context when no web request is available. Used in ishell, or
127 ## requests in context when no web request is available. Used in ishell, or
128 ## SSH calls. Set this for events to receive proper url for SSH calls.
128 ## SSH calls. Set this for events to receive proper url for SSH calls.
129 app.base_url = http://rhodecode.local
129 app.base_url = http://rhodecode.local
130
130
131 ## change this to unique ID for security
131 ## change this to unique ID for security
132 app_instance_uuid = rc-production
132 app_instance_uuid = rc-production
133
133
134 ## cut off limit for large diffs (size in bytes)
134 ## cut off limit for large diffs (size in bytes)
135 cut_off_limit_diff = 1024000
135 cut_off_limit_diff = 1024000
136 cut_off_limit_file = 256000
136 cut_off_limit_file = 256000
137
137
138 ## use cache version of scm repo everywhere
138 ## use cache version of scm repo everywhere
139 vcs_full_cache = false
139 vcs_full_cache = false
140
140
141 ## force https in RhodeCode, fixes https redirects, assumes it's always https
141 ## force https in RhodeCode, fixes https redirects, assumes it's always https
142 ## Normally this is controlled by proper http flags sent from http server
142 ## Normally this is controlled by proper http flags sent from http server
143 force_https = false
143 force_https = false
144
144
145 ## use Strict-Transport-Security headers
145 ## use Strict-Transport-Security headers
146 use_htsts = false
146 use_htsts = false
147
147
148 # Set to true if your repos are exposed using the dumb protocol
148 # Set to true if your repos are exposed using the dumb protocol
149 git_update_server_info = false
149 git_update_server_info = false
150
150
151 ## RSS/ATOM feed options
151 ## RSS/ATOM feed options
152 rss_cut_off_limit = 256000
152 rss_cut_off_limit = 256000
153 rss_items_per_page = 10
153 rss_items_per_page = 10
154 rss_include_diff = false
154 rss_include_diff = false
155
155
156 ## gist URL alias, used to create nicer urls for gist. This should be an
156 ## gist URL alias, used to create nicer urls for gist. This should be an
157 ## url that does rewrites to _admin/gists/{gistid}.
157 ## url that does rewrites to _admin/gists/{gistid}.
158 ## example: http://gist.rhodecode.org/{gistid}. Empty means use the internal
158 ## example: http://gist.rhodecode.org/{gistid}. Empty means use the internal
159 ## RhodeCode url, ie. http[s]://rhodecode.server/_admin/gists/{gistid}
159 ## RhodeCode url, ie. http[s]://rhodecode.server/_admin/gists/{gistid}
160 gist_alias_url =
160 gist_alias_url =
161
161
162 ## List of views (using glob pattern syntax) that AUTH TOKENS could be
162 ## List of views (using glob pattern syntax) that AUTH TOKENS could be
163 ## used for access.
163 ## used for access.
164 ## Adding ?auth_token=TOKEN_HASH to the url authenticates this request as if it
164 ## Adding ?auth_token=TOKEN_HASH to the url authenticates this request as if it
165 ## came from the the logged in user who own this authentication token.
165 ## came from the the logged in user who own this authentication token.
166 ## Additionally @TOKEN syntaxt can be used to bound the view to specific
166 ## Additionally @TOKEN syntaxt can be used to bound the view to specific
167 ## authentication token. Such view would be only accessible when used together
167 ## authentication token. Such view would be only accessible when used together
168 ## with this authentication token
168 ## with this authentication token
169 ##
169 ##
170 ## list of all views can be found under `/_admin/permissions/auth_token_access`
170 ## list of all views can be found under `/_admin/permissions/auth_token_access`
171 ## The list should be "," separated and on a single line.
171 ## The list should be "," separated and on a single line.
172 ##
172 ##
173 ## Most common views to enable:
173 ## Most common views to enable:
174 # RepoCommitsView:repo_commit_download
174 # RepoCommitsView:repo_commit_download
175 # RepoCommitsView:repo_commit_patch
175 # RepoCommitsView:repo_commit_patch
176 # RepoCommitsView:repo_commit_raw
176 # RepoCommitsView:repo_commit_raw
177 # RepoCommitsView:repo_commit_raw@TOKEN
177 # RepoCommitsView:repo_commit_raw@TOKEN
178 # RepoFilesView:repo_files_diff
178 # RepoFilesView:repo_files_diff
179 # RepoFilesView:repo_archivefile
179 # RepoFilesView:repo_archivefile
180 # RepoFilesView:repo_file_raw
180 # RepoFilesView:repo_file_raw
181 # GistView:*
181 # GistView:*
182 api_access_controllers_whitelist =
182 api_access_controllers_whitelist =
183
183
184 ## default encoding used to convert from and to unicode
184 ## default encoding used to convert from and to unicode
185 ## can be also a comma separated list of encoding in case of mixed encodings
185 ## can be also a comma separated list of encoding in case of mixed encodings
186 default_encoding = UTF-8
186 default_encoding = UTF-8
187
187
188 ## instance-id prefix
188 ## instance-id prefix
189 ## a prefix key for this instance used for cache invalidation when running
189 ## a prefix key for this instance used for cache invalidation when running
190 ## multiple instances of rhodecode, make sure it's globally unique for
190 ## multiple instances of rhodecode, make sure it's globally unique for
191 ## all running rhodecode instances. Leave empty if you don't use it
191 ## all running rhodecode instances. Leave empty if you don't use it
192 instance_id =
192 instance_id =
193
193
194 ## Fallback authentication plugin. Set this to a plugin ID to force the usage
194 ## Fallback authentication plugin. Set this to a plugin ID to force the usage
195 ## of an authentication plugin also if it is disabled by it's settings.
195 ## of an authentication plugin also if it is disabled by it's settings.
196 ## This could be useful if you are unable to log in to the system due to broken
196 ## This could be useful if you are unable to log in to the system due to broken
197 ## authentication settings. Then you can enable e.g. the internal rhodecode auth
197 ## authentication settings. Then you can enable e.g. the internal rhodecode auth
198 ## module to log in again and fix the settings.
198 ## module to log in again and fix the settings.
199 ##
199 ##
200 ## Available builtin plugin IDs (hash is part of the ID):
200 ## Available builtin plugin IDs (hash is part of the ID):
201 ## egg:rhodecode-enterprise-ce#rhodecode
201 ## egg:rhodecode-enterprise-ce#rhodecode
202 ## egg:rhodecode-enterprise-ce#pam
202 ## egg:rhodecode-enterprise-ce#pam
203 ## egg:rhodecode-enterprise-ce#ldap
203 ## egg:rhodecode-enterprise-ce#ldap
204 ## egg:rhodecode-enterprise-ce#jasig_cas
204 ## egg:rhodecode-enterprise-ce#jasig_cas
205 ## egg:rhodecode-enterprise-ce#headers
205 ## egg:rhodecode-enterprise-ce#headers
206 ## egg:rhodecode-enterprise-ce#crowd
206 ## egg:rhodecode-enterprise-ce#crowd
207 #rhodecode.auth_plugin_fallback = egg:rhodecode-enterprise-ce#rhodecode
207 #rhodecode.auth_plugin_fallback = egg:rhodecode-enterprise-ce#rhodecode
208
208
209 ## alternative return HTTP header for failed authentication. Default HTTP
209 ## alternative return HTTP header for failed authentication. Default HTTP
210 ## response is 401 HTTPUnauthorized. Currently HG clients have troubles with
210 ## response is 401 HTTPUnauthorized. Currently HG clients have troubles with
211 ## handling that causing a series of failed authentication calls.
211 ## handling that causing a series of failed authentication calls.
212 ## Set this variable to 403 to return HTTPForbidden, or any other HTTP code
212 ## Set this variable to 403 to return HTTPForbidden, or any other HTTP code
213 ## This will be served instead of default 401 on bad authnetication
213 ## This will be served instead of default 401 on bad authnetication
214 auth_ret_code =
214 auth_ret_code =
215
215
216 ## use special detection method when serving auth_ret_code, instead of serving
216 ## use special detection method when serving auth_ret_code, instead of serving
217 ## ret_code directly, use 401 initially (Which triggers credentials prompt)
217 ## ret_code directly, use 401 initially (Which triggers credentials prompt)
218 ## and then serve auth_ret_code to clients
218 ## and then serve auth_ret_code to clients
219 auth_ret_code_detection = false
219 auth_ret_code_detection = false
220
220
221 ## locking return code. When repository is locked return this HTTP code. 2XX
221 ## locking return code. When repository is locked return this HTTP code. 2XX
222 ## codes don't break the transactions while 4XX codes do
222 ## codes don't break the transactions while 4XX codes do
223 lock_ret_code = 423
223 lock_ret_code = 423
224
224
225 ## allows to change the repository location in settings page
225 ## allows to change the repository location in settings page
226 allow_repo_location_change = true
226 allow_repo_location_change = true
227
227
228 ## allows to setup custom hooks in settings page
228 ## allows to setup custom hooks in settings page
229 allow_custom_hooks_settings = true
229 allow_custom_hooks_settings = true
230
230
231 ## generated license token, goto license page in RhodeCode settings to obtain
231 ## generated license token, goto license page in RhodeCode settings to obtain
232 ## new token
232 ## new token
233 license_token = abra-cada-bra1-rce3
233 license_token = abra-cada-bra1-rce3
234
234
235 ## supervisor connection uri, for managing supervisor and logs.
235 ## supervisor connection uri, for managing supervisor and logs.
236 supervisor.uri =
236 supervisor.uri =
237 ## supervisord group name/id we only want this RC instance to handle
237 ## supervisord group name/id we only want this RC instance to handle
238 supervisor.group_id = dev
238 supervisor.group_id = dev
239
239
240 ## Display extended labs settings
240 ## Display extended labs settings
241 labs_settings_active = true
241 labs_settings_active = true
242
242
243 ####################################
243 ####################################
244 ### CELERY CONFIG ####
244 ### CELERY CONFIG ####
245 ####################################
245 ####################################
246 use_celery = false
246 use_celery = false
247 broker.host = localhost
247 broker.host = localhost
248 broker.vhost = rabbitmqhost
248 broker.vhost = rabbitmqhost
249 broker.port = 5672
249 broker.port = 5672
250 broker.user = rabbitmq
250 broker.user = rabbitmq
251 broker.password = qweqwe
251 broker.password = qweqwe
252
252
253 celery.imports = rhodecode.lib.celerylib.tasks
253 celery.imports = rhodecode.lib.celerylib.tasks
254
254
255 celery.result.backend = amqp
255 celery.result.backend = amqp
256 celery.result.dburi = amqp://
256 celery.result.dburi = amqp://
257 celery.result.serialier = json
257 celery.result.serialier = json
258
258
259 #celery.send.task.error.emails = true
259 #celery.send.task.error.emails = true
260 #celery.amqp.task.result.expires = 18000
260 #celery.amqp.task.result.expires = 18000
261
261
262 celeryd.concurrency = 2
262 celeryd.concurrency = 2
263 #celeryd.log.file = celeryd.log
263 #celeryd.log.file = celeryd.log
264 celeryd.log.level = debug
264 celeryd.log.level = debug
265 celeryd.max.tasks.per.child = 1
265 celeryd.max.tasks.per.child = 1
266
266
267 ## tasks will never be sent to the queue, but executed locally instead.
267 ## tasks will never be sent to the queue, but executed locally instead.
268 celery.always.eager = false
268 celery.always.eager = false
269
269
270 ####################################
270 ####################################
271 ### BEAKER CACHE ####
271 ### BEAKER CACHE ####
272 ####################################
272 ####################################
273 # default cache dir for templates. Putting this into a ramdisk
273 # default cache dir for templates. Putting this into a ramdisk
274 ## can boost performance, eg. %(here)s/data_ramdisk
274 ## can boost performance, eg. %(here)s/data_ramdisk
275 cache_dir = %(here)s/data
275 cache_dir = %(here)s/data
276
276
277 ## locking and default file storage for Beaker. Putting this into a ramdisk
277 ## locking and default file storage for Beaker. Putting this into a ramdisk
278 ## can boost performance, eg. %(here)s/data_ramdisk/cache/beaker_data
278 ## can boost performance, eg. %(here)s/data_ramdisk/cache/beaker_data
279 beaker.cache.data_dir = %(here)s/rc/data/cache/beaker_data
279 beaker.cache.data_dir = %(here)s/rc/data/cache/beaker_data
280 beaker.cache.lock_dir = %(here)s/rc/data/cache/beaker_lock
280 beaker.cache.lock_dir = %(here)s/rc/data/cache/beaker_lock
281
281
282 beaker.cache.regions = long_term
282 beaker.cache.regions = long_term
283
283
284 beaker.cache.long_term.type = memory
284 beaker.cache.long_term.type = memory
285 beaker.cache.long_term.expire = 36000
285 beaker.cache.long_term.expire = 36000
286 beaker.cache.long_term.key_length = 256
286 beaker.cache.long_term.key_length = 256
287
287
288
288
289 #####################################
289 #####################################
290 ### DOGPILE CACHE ####
290 ### DOGPILE CACHE ####
291 #####################################
291 #####################################
292
292
293 ## permission tree cache settings
293 ## permission tree cache settings
294 rc_cache.cache_perms.backend = dogpile.cache.rc.file_namespace
294 rc_cache.cache_perms.backend = dogpile.cache.rc.file_namespace
295 rc_cache.cache_perms.expiration_time = 0
295 rc_cache.cache_perms.expiration_time = 0
296 rc_cache.cache_perms.arguments.filename = /tmp/rc_cache_1
296 rc_cache.cache_perms.arguments.filename = /tmp/rc_cache_1
297
297
298
298
299 ## cache settings for SQL queries
299 ## cache settings for SQL queries
300 rc_cache.sql_cache_short.backend = dogpile.cache.rc.memory_lru
300 rc_cache.sql_cache_short.backend = dogpile.cache.rc.memory_lru
301 rc_cache.sql_cache_short.expiration_time = 0
301 rc_cache.sql_cache_short.expiration_time = 0
302
302
303
303
304 ####################################
304 ####################################
305 ### BEAKER SESSION ####
305 ### BEAKER SESSION ####
306 ####################################
306 ####################################
307
307
308 ## .session.type is type of storage options for the session, current allowed
308 ## .session.type is type of storage options for the session, current allowed
309 ## types are file, ext:memcached, ext:database, and memory (default).
309 ## types are file, ext:memcached, ext:database, and memory (default).
310 beaker.session.type = file
310 beaker.session.type = file
311 beaker.session.data_dir = %(here)s/rc/data/sessions/data
311 beaker.session.data_dir = %(here)s/rc/data/sessions/data
312
312
313 ## db based session, fast, and allows easy management over logged in users
313 ## db based session, fast, and allows easy management over logged in users
314 #beaker.session.type = ext:database
314 #beaker.session.type = ext:database
315 #beaker.session.table_name = db_session
315 #beaker.session.table_name = db_session
316 #beaker.session.sa.url = postgresql://postgres:secret@localhost/rhodecode
316 #beaker.session.sa.url = postgresql://postgres:secret@localhost/rhodecode
317 #beaker.session.sa.url = mysql://root:secret@127.0.0.1/rhodecode
317 #beaker.session.sa.url = mysql://root:secret@127.0.0.1/rhodecode
318 #beaker.session.sa.pool_recycle = 3600
318 #beaker.session.sa.pool_recycle = 3600
319 #beaker.session.sa.echo = false
319 #beaker.session.sa.echo = false
320
320
321 beaker.session.key = rhodecode
321 beaker.session.key = rhodecode
322 beaker.session.secret = test-rc-uytcxaz
322 beaker.session.secret = test-rc-uytcxaz
323 beaker.session.lock_dir = %(here)s/rc/data/sessions/lock
323 beaker.session.lock_dir = %(here)s/rc/data/sessions/lock
324
324
325 ## Secure encrypted cookie. Requires AES and AES python libraries
325 ## Secure encrypted cookie. Requires AES and AES python libraries
326 ## you must disable beaker.session.secret to use this
326 ## you must disable beaker.session.secret to use this
327 #beaker.session.encrypt_key = key_for_encryption
327 #beaker.session.encrypt_key = key_for_encryption
328 #beaker.session.validate_key = validation_key
328 #beaker.session.validate_key = validation_key
329
329
330 ## sets session as invalid(also logging out user) if it haven not been
330 ## sets session as invalid(also logging out user) if it haven not been
331 ## accessed for given amount of time in seconds
331 ## accessed for given amount of time in seconds
332 beaker.session.timeout = 2592000
332 beaker.session.timeout = 2592000
333 beaker.session.httponly = true
333 beaker.session.httponly = true
334 ## Path to use for the cookie. Set to prefix if you use prefix middleware
334 ## Path to use for the cookie. Set to prefix if you use prefix middleware
335 #beaker.session.cookie_path = /custom_prefix
335 #beaker.session.cookie_path = /custom_prefix
336
336
337 ## uncomment for https secure cookie
337 ## uncomment for https secure cookie
338 beaker.session.secure = false
338 beaker.session.secure = false
339
339
340 ## auto save the session to not to use .save()
340 ## auto save the session to not to use .save()
341 beaker.session.auto = false
341 beaker.session.auto = false
342
342
343 ## default cookie expiration time in seconds, set to `true` to set expire
343 ## default cookie expiration time in seconds, set to `true` to set expire
344 ## at browser close
344 ## at browser close
345 #beaker.session.cookie_expires = 3600
345 #beaker.session.cookie_expires = 3600
346
346
347 ###################################
347 ###################################
348 ## SEARCH INDEXING CONFIGURATION ##
348 ## SEARCH INDEXING CONFIGURATION ##
349 ###################################
349 ###################################
350 ## Full text search indexer is available in rhodecode-tools under
350 ## Full text search indexer is available in rhodecode-tools under
351 ## `rhodecode-tools index` command
351 ## `rhodecode-tools index` command
352
352
353 ## WHOOSH Backend, doesn't require additional services to run
353 ## WHOOSH Backend, doesn't require additional services to run
354 ## it works good with few dozen repos
354 ## it works good with few dozen repos
355 search.module = rhodecode.lib.index.whoosh
355 search.module = rhodecode.lib.index.whoosh
356 search.location = %(here)s/data/index
356 search.location = %(here)s/data/index
357
357
358 ########################################
358 ########################################
359 ### CHANNELSTREAM CONFIG ####
359 ### CHANNELSTREAM CONFIG ####
360 ########################################
360 ########################################
361 ## channelstream enables persistent connections and live notification
361 ## channelstream enables persistent connections and live notification
362 ## in the system. It's also used by the chat system
362 ## in the system. It's also used by the chat system
363
363
364 channelstream.enabled = false
364 channelstream.enabled = false
365
365
366 ## server address for channelstream server on the backend
366 ## server address for channelstream server on the backend
367 channelstream.server = 127.0.0.1:9800
367 channelstream.server = 127.0.0.1:9800
368 ## location of the channelstream server from outside world
368 ## location of the channelstream server from outside world
369 ## use ws:// for http or wss:// for https. This address needs to be handled
369 ## use ws:// for http or wss:// for https. This address needs to be handled
370 ## by external HTTP server such as Nginx or Apache
370 ## by external HTTP server such as Nginx or Apache
371 ## see nginx/apache configuration examples in our docs
371 ## see nginx/apache configuration examples in our docs
372 channelstream.ws_url = ws://rhodecode.yourserver.com/_channelstream
372 channelstream.ws_url = ws://rhodecode.yourserver.com/_channelstream
373 channelstream.secret = secret
373 channelstream.secret = secret
374 channelstream.history.location = %(here)s/channelstream_history
374 channelstream.history.location = %(here)s/channelstream_history
375
375
376 ## Internal application path that Javascript uses to connect into.
376 ## Internal application path that Javascript uses to connect into.
377 ## If you use proxy-prefix the prefix should be added before /_channelstream
377 ## If you use proxy-prefix the prefix should be added before /_channelstream
378 channelstream.proxy_path = /_channelstream
378 channelstream.proxy_path = /_channelstream
379
379
380
380
381 ###################################
381 ###################################
382 ## APPENLIGHT CONFIG ##
382 ## APPENLIGHT CONFIG ##
383 ###################################
383 ###################################
384
384
385 ## Appenlight is tailored to work with RhodeCode, see
385 ## Appenlight is tailored to work with RhodeCode, see
386 ## http://appenlight.com for details how to obtain an account
386 ## http://appenlight.com for details how to obtain an account
387
387
388 ## appenlight integration enabled
388 ## appenlight integration enabled
389 appenlight = false
389 appenlight = false
390
390
391 appenlight.server_url = https://api.appenlight.com
391 appenlight.server_url = https://api.appenlight.com
392 appenlight.api_key = YOUR_API_KEY
392 appenlight.api_key = YOUR_API_KEY
393 #appenlight.transport_config = https://api.appenlight.com?threaded=1&timeout=5
393 #appenlight.transport_config = https://api.appenlight.com?threaded=1&timeout=5
394
394
395 # used for JS client
395 # used for JS client
396 appenlight.api_public_key = YOUR_API_PUBLIC_KEY
396 appenlight.api_public_key = YOUR_API_PUBLIC_KEY
397
397
398 ## TWEAK AMOUNT OF INFO SENT HERE
398 ## TWEAK AMOUNT OF INFO SENT HERE
399
399
400 ## enables 404 error logging (default False)
400 ## enables 404 error logging (default False)
401 appenlight.report_404 = false
401 appenlight.report_404 = false
402
402
403 ## time in seconds after request is considered being slow (default 1)
403 ## time in seconds after request is considered being slow (default 1)
404 appenlight.slow_request_time = 1
404 appenlight.slow_request_time = 1
405
405
406 ## record slow requests in application
406 ## record slow requests in application
407 ## (needs to be enabled for slow datastore recording and time tracking)
407 ## (needs to be enabled for slow datastore recording and time tracking)
408 appenlight.slow_requests = true
408 appenlight.slow_requests = true
409
409
410 ## enable hooking to application loggers
410 ## enable hooking to application loggers
411 appenlight.logging = true
411 appenlight.logging = true
412
412
413 ## minimum log level for log capture
413 ## minimum log level for log capture
414 appenlight.logging.level = WARNING
414 appenlight.logging.level = WARNING
415
415
416 ## send logs only from erroneous/slow requests
416 ## send logs only from erroneous/slow requests
417 ## (saves API quota for intensive logging)
417 ## (saves API quota for intensive logging)
418 appenlight.logging_on_error = false
418 appenlight.logging_on_error = false
419
419
420 ## list of additonal keywords that should be grabbed from environ object
420 ## list of additonal keywords that should be grabbed from environ object
421 ## can be string with comma separated list of words in lowercase
421 ## can be string with comma separated list of words in lowercase
422 ## (by default client will always send following info:
422 ## (by default client will always send following info:
423 ## 'REMOTE_USER', 'REMOTE_ADDR', 'SERVER_NAME', 'CONTENT_TYPE' + all keys that
423 ## 'REMOTE_USER', 'REMOTE_ADDR', 'SERVER_NAME', 'CONTENT_TYPE' + all keys that
424 ## start with HTTP* this list be extended with additional keywords here
424 ## start with HTTP* this list be extended with additional keywords here
425 appenlight.environ_keys_whitelist =
425 appenlight.environ_keys_whitelist =
426
426
427 ## list of keywords that should be blanked from request object
427 ## list of keywords that should be blanked from request object
428 ## can be string with comma separated list of words in lowercase
428 ## can be string with comma separated list of words in lowercase
429 ## (by default client will always blank keys that contain following words
429 ## (by default client will always blank keys that contain following words
430 ## 'password', 'passwd', 'pwd', 'auth_tkt', 'secret', 'csrf'
430 ## 'password', 'passwd', 'pwd', 'auth_tkt', 'secret', 'csrf'
431 ## this list be extended with additional keywords set here
431 ## this list be extended with additional keywords set here
432 appenlight.request_keys_blacklist =
432 appenlight.request_keys_blacklist =
433
433
434 ## list of namespaces that should be ignores when gathering log entries
434 ## list of namespaces that should be ignores when gathering log entries
435 ## can be string with comma separated list of namespaces
435 ## can be string with comma separated list of namespaces
436 ## (by default the client ignores own entries: appenlight_client.client)
436 ## (by default the client ignores own entries: appenlight_client.client)
437 appenlight.log_namespace_blacklist =
437 appenlight.log_namespace_blacklist =
438
438
439
439
440 ################################################################################
440 ################################################################################
441 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
441 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
442 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
442 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
443 ## execute malicious code after an exception is raised. ##
443 ## execute malicious code after an exception is raised. ##
444 ################################################################################
444 ################################################################################
445 set debug = false
445 set debug = false
446
446
447
447
448 ##############
448 ##############
449 ## STYLING ##
449 ## STYLING ##
450 ##############
450 ##############
451 debug_style = false
451 debug_style = false
452
452
453 ###########################################
453 ###########################################
454 ### MAIN RHODECODE DATABASE CONFIG ###
454 ### MAIN RHODECODE DATABASE CONFIG ###
455 ###########################################
455 ###########################################
456 #sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode_test.db?timeout=30
456 #sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode_test.db?timeout=30
457 #sqlalchemy.db1.url = postgresql://postgres:qweqwe@localhost/rhodecode_test
457 #sqlalchemy.db1.url = postgresql://postgres:qweqwe@localhost/rhodecode_test
458 #sqlalchemy.db1.url = mysql://root:qweqwe@localhost/rhodecode_test
458 #sqlalchemy.db1.url = mysql://root:qweqwe@localhost/rhodecode_test
459 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode_test.db?timeout=30
459 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode_test.db?timeout=30
460
460
461 # see sqlalchemy docs for other advanced settings
461 # see sqlalchemy docs for other advanced settings
462
462
463 ## print the sql statements to output
463 ## print the sql statements to output
464 sqlalchemy.db1.echo = false
464 sqlalchemy.db1.echo = false
465 ## recycle the connections after this amount of seconds
465 ## recycle the connections after this amount of seconds
466 sqlalchemy.db1.pool_recycle = 3600
466 sqlalchemy.db1.pool_recycle = 3600
467
467
468 ## the number of connections to keep open inside the connection pool.
468 ## the number of connections to keep open inside the connection pool.
469 ## 0 indicates no limit
469 ## 0 indicates no limit
470 #sqlalchemy.db1.pool_size = 5
470 #sqlalchemy.db1.pool_size = 5
471
471
472 ## the number of connections to allow in connection pool "overflow", that is
472 ## the number of connections to allow in connection pool "overflow", that is
473 ## connections that can be opened above and beyond the pool_size setting,
473 ## connections that can be opened above and beyond the pool_size setting,
474 ## which defaults to five.
474 ## which defaults to five.
475 #sqlalchemy.db1.max_overflow = 10
475 #sqlalchemy.db1.max_overflow = 10
476
476
477
477
478 ##################
478 ##################
479 ### VCS CONFIG ###
479 ### VCS CONFIG ###
480 ##################
480 ##################
481 vcs.server.enable = true
481 vcs.server.enable = true
482 vcs.server = localhost:9901
482 vcs.server = localhost:9901
483
483
484 ## Web server connectivity protocol, responsible for web based VCS operatations
484 ## Web server connectivity protocol, responsible for web based VCS operatations
485 ## Available protocols are:
485 ## Available protocols are:
486 ## `http` - use http-rpc backend (default)
486 ## `http` - use http-rpc backend (default)
487 vcs.server.protocol = http
487 vcs.server.protocol = http
488
488
489 ## Push/Pull operations protocol, available options are:
489 ## Push/Pull operations protocol, available options are:
490 ## `http` - use http-rpc backend (default)
490 ## `http` - use http-rpc backend (default)
491 ## `vcsserver.scm_app` - internal app (EE only)
491 ## `vcsserver.scm_app` - internal app (EE only)
492 vcs.scm_app_implementation = http
492 vcs.scm_app_implementation = http
493
493
494 ## Push/Pull operations hooks protocol, available options are:
494 ## Push/Pull operations hooks protocol, available options are:
495 ## `http` - use http-rpc backend (default)
495 ## `http` - use http-rpc backend (default)
496 vcs.hooks.protocol = http
496 vcs.hooks.protocol = http
497 vcs.hooks.host = 127.0.0.1
497 vcs.hooks.host = 127.0.0.1
498
498
499 vcs.server.log_level = debug
499
500 ## Start VCSServer with this instance as a subprocess, Useful for development
500 ## Start VCSServer with this instance as a subprocess, Useful for development
501 vcs.start_server = false
501 vcs.start_server = false
502
502
503 ## List of enabled VCS backends, available options are:
503 ## List of enabled VCS backends, available options are:
504 ## `hg` - mercurial
504 ## `hg` - mercurial
505 ## `git` - git
505 ## `git` - git
506 ## `svn` - subversion
506 ## `svn` - subversion
507 vcs.backends = hg, git, svn
507 vcs.backends = hg, git, svn
508
508
509 vcs.connection_timeout = 3600
509 vcs.connection_timeout = 3600
510 ## Compatibility version when creating SVN repositories. Defaults to newest version when commented out.
510 ## Compatibility version when creating SVN repositories. Defaults to newest version when commented out.
511 ## Available options are: pre-1.4-compatible, pre-1.5-compatible, pre-1.6-compatible, pre-1.8-compatible, pre-1.9-compatible
511 ## Available options are: pre-1.4-compatible, pre-1.5-compatible, pre-1.6-compatible, pre-1.8-compatible, pre-1.9-compatible
512 #vcs.svn.compatible_version = pre-1.8-compatible
512 #vcs.svn.compatible_version = pre-1.8-compatible
513
513
514
514
515 ############################################################
515 ############################################################
516 ### Subversion proxy support (mod_dav_svn) ###
516 ### Subversion proxy support (mod_dav_svn) ###
517 ### Maps RhodeCode repo groups into SVN paths for Apache ###
517 ### Maps RhodeCode repo groups into SVN paths for Apache ###
518 ############################################################
518 ############################################################
519 ## Enable or disable the config file generation.
519 ## Enable or disable the config file generation.
520 svn.proxy.generate_config = false
520 svn.proxy.generate_config = false
521 ## Generate config file with `SVNListParentPath` set to `On`.
521 ## Generate config file with `SVNListParentPath` set to `On`.
522 svn.proxy.list_parent_path = true
522 svn.proxy.list_parent_path = true
523 ## Set location and file name of generated config file.
523 ## Set location and file name of generated config file.
524 svn.proxy.config_file_path = %(here)s/mod_dav_svn.conf
524 svn.proxy.config_file_path = %(here)s/mod_dav_svn.conf
525 ## Used as a prefix to the `Location` block in the generated config file.
525 ## Used as a prefix to the `Location` block in the generated config file.
526 ## In most cases it should be set to `/`.
526 ## In most cases it should be set to `/`.
527 svn.proxy.location_root = /
527 svn.proxy.location_root = /
528 ## Command to reload the mod dav svn configuration on change.
528 ## Command to reload the mod dav svn configuration on change.
529 ## Example: `/etc/init.d/apache2 reload`
529 ## Example: `/etc/init.d/apache2 reload`
530 #svn.proxy.reload_cmd = /etc/init.d/apache2 reload
530 #svn.proxy.reload_cmd = /etc/init.d/apache2 reload
531 ## If the timeout expires before the reload command finishes, the command will
531 ## If the timeout expires before the reload command finishes, the command will
532 ## be killed. Setting it to zero means no timeout. Defaults to 10 seconds.
532 ## be killed. Setting it to zero means no timeout. Defaults to 10 seconds.
533 #svn.proxy.reload_timeout = 10
533 #svn.proxy.reload_timeout = 10
534
534
535 ############################################################
535 ############################################################
536 ### SSH Support Settings ###
536 ### SSH Support Settings ###
537 ############################################################
537 ############################################################
538
538
539 ## Defines if the authorized_keys file should be written on any change of
539 ## Defines if the authorized_keys file should be written on any change of
540 ## user ssh keys, setting this to false also disables posibility of adding
540 ## user ssh keys, setting this to false also disables posibility of adding
541 ## ssh keys for users from web interface.
541 ## ssh keys for users from web interface.
542 ssh.generate_authorized_keyfile = true
542 ssh.generate_authorized_keyfile = true
543
543
544 ## Options for ssh, default is `no-pty,no-port-forwarding,no-X11-forwarding,no-agent-forwarding`
544 ## Options for ssh, default is `no-pty,no-port-forwarding,no-X11-forwarding,no-agent-forwarding`
545 # ssh.authorized_keys_ssh_opts =
545 # ssh.authorized_keys_ssh_opts =
546
546
547 ## File to generate the authorized keys together with options
547 ## File to generate the authorized keys together with options
548 ## It is possible to have multiple key files specified in `sshd_config` e.g.
548 ## It is possible to have multiple key files specified in `sshd_config` e.g.
549 ## AuthorizedKeysFile %h/.ssh/authorized_keys %h/.ssh/authorized_keys_rhodecode
549 ## AuthorizedKeysFile %h/.ssh/authorized_keys %h/.ssh/authorized_keys_rhodecode
550 ssh.authorized_keys_file_path = %(here)s/rc/authorized_keys_rhodecode
550 ssh.authorized_keys_file_path = %(here)s/rc/authorized_keys_rhodecode
551
551
552 ## Command to execute the SSH wrapper. The binary is available in the
552 ## Command to execute the SSH wrapper. The binary is available in the
553 ## rhodecode installation directory.
553 ## rhodecode installation directory.
554 ## e.g ~/.rccontrol/community-1/profile/bin/rc-ssh-wrapper
554 ## e.g ~/.rccontrol/community-1/profile/bin/rc-ssh-wrapper
555 ssh.wrapper_cmd = ~/.rccontrol/community-1/rc-ssh-wrapper
555 ssh.wrapper_cmd = ~/.rccontrol/community-1/rc-ssh-wrapper
556
556
557 ## Allow shell when executing the ssh-wrapper command
557 ## Allow shell when executing the ssh-wrapper command
558 ssh.wrapper_cmd_allow_shell = false
558 ssh.wrapper_cmd_allow_shell = false
559
559
560 ## Enables logging, and detailed output send back to the client. Useful for
560 ## Enables logging, and detailed output send back to the client. Useful for
561 ## debugging, shouldn't be used in production.
561 ## debugging, shouldn't be used in production.
562 ssh.enable_debug_logging = false
562 ssh.enable_debug_logging = false
563
563
564 ## Paths to binary executrables, by default they are the names, but we can
564 ## Paths to binary executrables, by default they are the names, but we can
565 ## override them if we want to use a custom one
565 ## override them if we want to use a custom one
566 ssh.executable.hg = ~/.rccontrol/vcsserver-1/profile/bin/hg
566 ssh.executable.hg = ~/.rccontrol/vcsserver-1/profile/bin/hg
567 ssh.executable.git = ~/.rccontrol/vcsserver-1/profile/bin/git
567 ssh.executable.git = ~/.rccontrol/vcsserver-1/profile/bin/git
568 ssh.executable.svn = ~/.rccontrol/vcsserver-1/profile/bin/svnserve
568 ssh.executable.svn = ~/.rccontrol/vcsserver-1/profile/bin/svnserve
569
569
570 ## Enables SSH key generator web interface. Disabling this still allows users
570 ## Enables SSH key generator web interface. Disabling this still allows users
571 ## to add their own keys.
571 ## to add their own keys.
572 ssh.enable_ui_key_generator = true
572 ssh.enable_ui_key_generator = true
573
573
574
574
575 ## Dummy marker to add new entries after.
575 ## Dummy marker to add new entries after.
576 ## Add any custom entries below. Please don't remove.
576 ## Add any custom entries below. Please don't remove.
577 custom.conf = 1
577 custom.conf = 1
578
578
579
579
580 ################################
580 ################################
581 ### LOGGING CONFIGURATION ####
581 ### LOGGING CONFIGURATION ####
582 ################################
582 ################################
583 [loggers]
583 [loggers]
584 keys = root, sqlalchemy, beaker, rhodecode, ssh_wrapper
584 keys = root, sqlalchemy, beaker, rhodecode, ssh_wrapper
585
585
586 [handlers]
586 [handlers]
587 keys = console, console_sql
587 keys = console, console_sql
588
588
589 [formatters]
589 [formatters]
590 keys = generic, color_formatter, color_formatter_sql
590 keys = generic, color_formatter, color_formatter_sql
591
591
592 #############
592 #############
593 ## LOGGERS ##
593 ## LOGGERS ##
594 #############
594 #############
595 [logger_root]
595 [logger_root]
596 level = NOTSET
596 level = NOTSET
597 handlers = console
597 handlers = console
598
598
599 [logger_routes]
599 [logger_routes]
600 level = DEBUG
600 level = DEBUG
601 handlers =
601 handlers =
602 qualname = routes.middleware
602 qualname = routes.middleware
603 ## "level = DEBUG" logs the route matched and routing variables.
603 ## "level = DEBUG" logs the route matched and routing variables.
604 propagate = 1
604 propagate = 1
605
605
606 [logger_beaker]
606 [logger_beaker]
607 level = DEBUG
607 level = DEBUG
608 handlers =
608 handlers =
609 qualname = beaker.container
609 qualname = beaker.container
610 propagate = 1
610 propagate = 1
611
611
612 [logger_rhodecode]
612 [logger_rhodecode]
613 level = DEBUG
613 level = DEBUG
614 handlers =
614 handlers =
615 qualname = rhodecode
615 qualname = rhodecode
616 propagate = 1
616 propagate = 1
617
617
618 [logger_sqlalchemy]
618 [logger_sqlalchemy]
619 level = ERROR
619 level = ERROR
620 handlers = console_sql
620 handlers = console_sql
621 qualname = sqlalchemy.engine
621 qualname = sqlalchemy.engine
622 propagate = 0
622 propagate = 0
623
623
624 [logger_ssh_wrapper]
624 [logger_ssh_wrapper]
625 level = DEBUG
625 level = DEBUG
626 handlers =
626 handlers =
627 qualname = ssh_wrapper
627 qualname = ssh_wrapper
628 propagate = 1
628 propagate = 1
629
629
630
630
631 ##############
631 ##############
632 ## HANDLERS ##
632 ## HANDLERS ##
633 ##############
633 ##############
634
634
635 [handler_console]
635 [handler_console]
636 class = StreamHandler
636 class = StreamHandler
637 args = (sys.stderr,)
637 args = (sys.stderr,)
638 level = DEBUG
638 level = DEBUG
639 formatter = generic
639 formatter = generic
640
640
641 [handler_console_sql]
641 [handler_console_sql]
642 class = StreamHandler
642 class = StreamHandler
643 args = (sys.stderr,)
643 args = (sys.stderr,)
644 level = WARN
644 level = WARN
645 formatter = generic
645 formatter = generic
646
646
647 ################
647 ################
648 ## FORMATTERS ##
648 ## FORMATTERS ##
649 ################
649 ################
650
650
651 [formatter_generic]
651 [formatter_generic]
652 class = rhodecode.lib.logging_formatter.ExceptionAwareFormatter
652 class = rhodecode.lib.logging_formatter.ExceptionAwareFormatter
653 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
653 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
654 datefmt = %Y-%m-%d %H:%M:%S
654 datefmt = %Y-%m-%d %H:%M:%S
655
655
656 [formatter_color_formatter]
656 [formatter_color_formatter]
657 class = rhodecode.lib.logging_formatter.ColorFormatter
657 class = rhodecode.lib.logging_formatter.ColorFormatter
658 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
658 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
659 datefmt = %Y-%m-%d %H:%M:%S
659 datefmt = %Y-%m-%d %H:%M:%S
660
660
661 [formatter_color_formatter_sql]
661 [formatter_color_formatter_sql]
662 class = rhodecode.lib.logging_formatter.ColorFormatterSql
662 class = rhodecode.lib.logging_formatter.ColorFormatterSql
663 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
663 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
664 datefmt = %Y-%m-%d %H:%M:%S
664 datefmt = %Y-%m-%d %H:%M:%S
General Comments 0
You need to be logged in to leave comments. Login now