##// END OF EJS Templates
Implemented whoosh index building as paster command....
marcink -
r683:341beaa9 beta
parent child Browse files
Show More
@@ -1,15 +1,15 b''
1 include rhodecode/config/deployment.ini_tmpl
1 include rhodecode/config/deployment.ini_tmpl
2
2
3 include README.rst
3 include README.rst
4 recursive-include rhodecode/i18n/ *
4 recursive-include rhodecode/i18n/ *
5
5
6 #images
6 #images
7 recursive-include rhodecode/public/css *
7 recursive-include rhodecode/public/css *
8 recursive-include rhodecode/public/images *
8 recursive-include rhodecode/public/images *
9 #js
9 #js
10 include rhodecode/public/js/yui2.js
10 include rhodecode/public/js/yui2a.js
11 include rhodecode/public/js/excanvas.min.js
11 include rhodecode/public/js/excanvas.min.js
12 include rhodecode/public/js/yui.flot.js
12 include rhodecode/public/js/yui.flot.js
13 include rhodecode/public/js/graph.js
13 include rhodecode/public/js/graph.js
14 #templates
14 #templates
15 recursive-include rhodecode/templates *
15 recursive-include rhodecode/templates *
@@ -1,174 +1,175 b''
1 ################################################################################
1 ################################################################################
2 ################################################################################
2 ################################################################################
3 # rhodecode - Pylons environment configuration #
3 # rhodecode - Pylons environment configuration #
4 # #
4 # #
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 ## Uncomment and replace with the address which should receive ##
11 ## Uncomment and replace with the address which should receive ##
12 ## any error reports after application crash ##
12 ## any error reports after application crash ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
14 ################################################################################
14 ################################################################################
15 #email_to = admin@localhost
15 #email_to = admin@localhost
16 #error_email_from = paste_error@localhost
16 #error_email_from = paste_error@localhost
17 #app_email_from = rhodecode-noreply@localhost
17 #app_email_from = rhodecode-noreply@localhost
18 #error_message =
18 #error_message =
19
19
20 #smtp_server = mail.server.com
20 #smtp_server = mail.server.com
21 #smtp_username =
21 #smtp_username =
22 #smtp_password =
22 #smtp_password =
23 #smtp_port =
23 #smtp_port =
24 #smtp_use_tls =
24 #smtp_use_tls =
25
25
26 [server:main]
26 [server:main]
27 ##nr of threads to spawn
27 ##nr of threads to spawn
28 threadpool_workers = 5
28 threadpool_workers = 5
29
29
30 ##max request before
30 ##max request before
31 threadpool_max_requests = 6
31 threadpool_max_requests = 6
32
32
33 ##option to use threads of process
33 ##option to use threads of process
34 use_threadpool = false
34 use_threadpool = false
35
35
36 use = egg:Paste#http
36 use = egg:Paste#http
37 host = 127.0.0.1
37 host = 127.0.0.1
38 port = 5000
38 port = 5000
39
39
40 [app:main]
40 [app:main]
41 use = egg:rhodecode
41 use = egg:rhodecode
42 full_stack = true
42 full_stack = true
43 static_files = true
43 static_files = true
44 lang=en
44 lang=en
45 cache_dir = %(here)s/data
45 cache_dir = %(here)s/data
46 index_dir = %(here)s/data/index
46
47
47 ####################################
48 ####################################
48 ### BEAKER CACHE ####
49 ### BEAKER CACHE ####
49 ####################################
50 ####################################
50 beaker.cache.data_dir=/%(here)s/data/cache/data
51 beaker.cache.data_dir=/%(here)s/data/cache/data
51 beaker.cache.lock_dir=/%(here)s/data/cache/lock
52 beaker.cache.lock_dir=/%(here)s/data/cache/lock
52 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
53 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
53
54
54 beaker.cache.super_short_term.type=memory
55 beaker.cache.super_short_term.type=memory
55 beaker.cache.super_short_term.expire=10
56 beaker.cache.super_short_term.expire=10
56
57
57 beaker.cache.short_term.type=memory
58 beaker.cache.short_term.type=memory
58 beaker.cache.short_term.expire=60
59 beaker.cache.short_term.expire=60
59
60
60 beaker.cache.long_term.type=memory
61 beaker.cache.long_term.type=memory
61 beaker.cache.long_term.expire=36000
62 beaker.cache.long_term.expire=36000
62
63
63
64
64 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.expire=5
66 beaker.cache.sql_cache_short.expire=5
66
67
67 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.expire=360
69 beaker.cache.sql_cache_med.expire=360
69
70
70 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.expire=3600
72 beaker.cache.sql_cache_long.expire=3600
72
73
73 ####################################
74 ####################################
74 ### BEAKER SESSION ####
75 ### BEAKER SESSION ####
75 ####################################
76 ####################################
76 ## Type of storage used for the session, current types are
77 ## Type of storage used for the session, current types are
77 ## "dbm", "file", "memcached", "database", and "memory".
78 ## "dbm", "file", "memcached", "database", and "memory".
78 ## The storage uses the Container API
79 ## The storage uses the Container API
79 ##that is also used by the cache system.
80 ##that is also used by the cache system.
80 beaker.session.type = file
81 beaker.session.type = file
81
82
82 beaker.session.key = rhodecode
83 beaker.session.key = rhodecode
83 beaker.session.secret = g654dcno0-9873jhgfreyu
84 beaker.session.secret = g654dcno0-9873jhgfreyu
84 beaker.session.timeout = 36000
85 beaker.session.timeout = 36000
85
86
86 ##auto save the session to not to use .save()
87 ##auto save the session to not to use .save()
87 beaker.session.auto = False
88 beaker.session.auto = False
88
89
89 ##true exire at browser close
90 ##true exire at browser close
90 #beaker.session.cookie_expires = 3600
91 #beaker.session.cookie_expires = 3600
91
92
92
93
93 ################################################################################
94 ################################################################################
94 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## execute malicious code after an exception is raised. ##
97 ## execute malicious code after an exception is raised. ##
97 ################################################################################
98 ################################################################################
98 #set debug = false
99 #set debug = false
99
100
100 ##################################
101 ##################################
101 ### LOGVIEW CONFIG ###
102 ### LOGVIEW CONFIG ###
102 ##################################
103 ##################################
103 logview.sqlalchemy = #faa
104 logview.sqlalchemy = #faa
104 logview.pylons.templating = #bfb
105 logview.pylons.templating = #bfb
105 logview.pylons.util = #eee
106 logview.pylons.util = #eee
106
107
107 #########################################################
108 #########################################################
108 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 #########################################################
110 #########################################################
110 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.pool_recycle = 3600
113 #sqlalchemy.db1.pool_recycle = 3600
113 sqlalchemy.convert_unicode = true
114 sqlalchemy.convert_unicode = true
114
115
115 ################################
116 ################################
116 ### LOGGING CONFIGURATION ####
117 ### LOGGING CONFIGURATION ####
117 ################################
118 ################################
118 [loggers]
119 [loggers]
119 keys = root, routes, rhodecode, sqlalchemy
120 keys = root, routes, rhodecode, sqlalchemy
120
121
121 [handlers]
122 [handlers]
122 keys = console
123 keys = console
123
124
124 [formatters]
125 [formatters]
125 keys = generic,color_formatter
126 keys = generic,color_formatter
126
127
127 #############
128 #############
128 ## LOGGERS ##
129 ## LOGGERS ##
129 #############
130 #############
130 [logger_root]
131 [logger_root]
131 level = NOTSET
132 level = NOTSET
132 handlers = console
133 handlers = console
133
134
134 [logger_routes]
135 [logger_routes]
135 level = DEBUG
136 level = DEBUG
136 handlers = console
137 handlers = console
137 qualname = routes.middleware
138 qualname = routes.middleware
138 # "level = DEBUG" logs the route matched and routing variables.
139 # "level = DEBUG" logs the route matched and routing variables.
139 propagate = 0
140 propagate = 0
140
141
141 [logger_rhodecode]
142 [logger_rhodecode]
142 level = DEBUG
143 level = DEBUG
143 handlers = console
144 handlers = console
144 qualname = rhodecode
145 qualname = rhodecode
145 propagate = 0
146 propagate = 0
146
147
147 [logger_sqlalchemy]
148 [logger_sqlalchemy]
148 level = ERROR
149 level = ERROR
149 handlers = console
150 handlers = console
150 qualname = sqlalchemy.engine
151 qualname = sqlalchemy.engine
151 propagate = 0
152 propagate = 0
152
153
153 ##############
154 ##############
154 ## HANDLERS ##
155 ## HANDLERS ##
155 ##############
156 ##############
156
157
157 [handler_console]
158 [handler_console]
158 class = StreamHandler
159 class = StreamHandler
159 args = (sys.stderr,)
160 args = (sys.stderr,)
160 level = NOTSET
161 level = NOTSET
161 formatter = color_formatter
162 formatter = color_formatter
162
163
163 ################
164 ################
164 ## FORMATTERS ##
165 ## FORMATTERS ##
165 ################
166 ################
166
167
167 [formatter_generic]
168 [formatter_generic]
168 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 datefmt = %Y-%m-%d %H:%M:%S
170 datefmt = %Y-%m-%d %H:%M:%S
170
171
171 [formatter_color_formatter]
172 [formatter_color_formatter]
172 class=rhodecode.lib.colored_formatter.ColorFormatter
173 class=rhodecode.lib.colored_formatter.ColorFormatter
173 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 datefmt = %Y-%m-%d %H:%M:%S No newline at end of file
175 datefmt = %Y-%m-%d %H:%M:%S
@@ -1,68 +1,69 b''
1 .. _changelog:
1 .. _changelog:
2
2
3 Changelog
3 Changelog
4 =========
4 =========
5
5
6 1.1.0 (**2010-XX-XX**)
6 1.1.0 (**2010-XX-XX**)
7 ----------------------
7 ----------------------
8 - git support with push/pull via RhodeCode web interface
8 - git support with push/pull via RhodeCode web interface
9 - rewrite of internals for vcs >=0.1.9
9 - rewrite of internals for vcs >=0.1.9
10 - anonymous access
10 - anonymous access
11 - performance upgrade for cached repos list - each repository has it's own
11 - performance upgrade for cached repos list - each repository has it's own
12 cache that's invalidated when needed.
12 cache that's invalidated when needed.
13 - main page quick filter for filtering repositories
13 - main page quick filter for filtering repositories
14 - more detailed action logger (based on hooks) with pushed changesets lists
14 - more detailed action logger (based on hooks) with pushed changesets lists
15 and options to disable those hooks from admin panel
15 and options to disable those hooks from admin panel
16 - a lot of fixes and tweaks for file browser
16 - a lot of fixes and tweaks for file browser
17 - introduced new enhanced changelog for merges that shows more accurate results
17 - introduced new enhanced changelog for merges that shows more accurate results
18 - gui optimizations, fixed application width to 1024px
18 - gui optimizations, fixed application width to 1024px
19 - numerous small bugfixes
19 - numerous small bugfixes
20 - whoosh index moved to paster command
20
21
21 1.0.2 (**2010-11-12**)
22 1.0.2 (**2010-11-12**)
22 ----------------------
23 ----------------------
23
24
24 - fixed #59 missing graph.js
25 - fixed #59 missing graph.js
25 - fixed repo_size crash when repository had broken symlinks
26 - fixed repo_size crash when repository had broken symlinks
26 - fixed python2.5 crashes.
27 - fixed python2.5 crashes.
27 - tested under python2.7
28 - tested under python2.7
28 - bumped sqlalchemy and celery versions
29 - bumped sqlalchemy and celery versions
29
30
30 1.0.1 (**2010-11-10**)
31 1.0.1 (**2010-11-10**)
31 ----------------------
32 ----------------------
32
33
33 - fixed #53 python2.5 incompatible enumerate calls
34 - fixed #53 python2.5 incompatible enumerate calls
34 - fixed #52 disable mercurial extension for web
35 - fixed #52 disable mercurial extension for web
35 - fixed #51 deleting repositories don't delete it's dependent objects
36 - fixed #51 deleting repositories don't delete it's dependent objects
36 - small css updated
37 - small css updated
37
38
38 1.0.0 (**2010-11-02**)
39 1.0.0 (**2010-11-02**)
39 ----------------------
40 ----------------------
40
41
41 - security bugfix simplehg wasn't checking for permissions on commands
42 - security bugfix simplehg wasn't checking for permissions on commands
42 other than pull or push.
43 other than pull or push.
43 - fixed doubled messages after push or pull in admin journal
44 - fixed doubled messages after push or pull in admin journal
44 - templating and css corrections, fixed repo switcher on chrome, updated titles
45 - templating and css corrections, fixed repo switcher on chrome, updated titles
45 - admin menu accessible from options menu on repository view
46 - admin menu accessible from options menu on repository view
46 - permissions cached queries
47 - permissions cached queries
47
48
48 1.0.0rc4 (**2010-10-12**)
49 1.0.0rc4 (**2010-10-12**)
49 --------------------------
50 --------------------------
50
51
51 - fixed python2.5 missing simplejson imports (thanks to Jens BΓ€ckman)
52 - fixed python2.5 missing simplejson imports (thanks to Jens BΓ€ckman)
52 - removed cache_manager settings from sqlalchemy meta
53 - removed cache_manager settings from sqlalchemy meta
53 - added sqlalchemy cache settings to ini files
54 - added sqlalchemy cache settings to ini files
54 - validated password length and added second try of failure on paster setup-app
55 - validated password length and added second try of failure on paster setup-app
55 - fixed setup database destroy prompt even when there was no db
56 - fixed setup database destroy prompt even when there was no db
56
57
57
58
58 1.0.0rc3 (**2010-10-11**)
59 1.0.0rc3 (**2010-10-11**)
59 -------------------------
60 -------------------------
60
61
61 - fixed i18n during installation.
62 - fixed i18n during installation.
62
63
63 1.0.0rc2 (**2010-10-11**)
64 1.0.0rc2 (**2010-10-11**)
64 -------------------------
65 -------------------------
65
66
66 - Disabled dirsize in file browser, it's causing nasty bug when dir renames
67 - Disabled dirsize in file browser, it's causing nasty bug when dir renames
67 occure. After vcs is fixed it'll be put back again.
68 occure. After vcs is fixed it'll be put back again.
68 - templating/css rewrites, optimized css.
69 - templating/css rewrites, optimized css.
@@ -1,129 +1,148 b''
1 .. _setup:
1 .. _setup:
2
2
3 Setup
3 Setup
4 =====
4 =====
5
5
6
6
7 Setting up the application
7 Setting up the application
8 --------------------------
8 --------------------------
9
9
10 ::
10 ::
11
11
12 paster make-config RhodeCode production.ini
12 paster make-config RhodeCode production.ini
13
13
14 - This will create `production.ini` config inside the directory
14 - This will create `production.ini` config inside the directory
15 this config contain various settings for rhodecode, e.g port, email settings
15 this config contain various settings for rhodecode, e.g port, email settings
16 static files, cache and logging.
16 static files, cache and logging.
17
17
18 ::
18 ::
19
19
20 paster setup-app production.ini
20 paster setup-app production.ini
21
21
22 - This command will create all needed tables and an admin account.
22 - This command will create all needed tables and an admin account.
23 When asked for a path You can either use a new location of one with already
23 When asked for a path You can either use a new location of one with already
24 existing ones. RhodeCode will simply add all new found repositories to
24 existing ones. RhodeCode will simply add all new found repositories to
25 it's database. Also make sure You specify correct path to repositories.
25 it's database. Also make sure You specify correct path to repositories.
26 - Remember that the given path for mercurial_ repositories must be write
26 - Remember that the given path for mercurial_ repositories must be write
27 accessible for the application. It's very important since RhodeCode web interface
27 accessible for the application. It's very important since RhodeCode web interface
28 will work even without such an access but, when trying to do a push it'll
28 will work even without such an access but, when trying to do a push it'll
29 eventually fail with permission denied errors.
29 eventually fail with permission denied errors.
30 - Run
30 - Run
31
31
32 ::
32 ::
33
33
34 paster serve production.ini
34 paster serve production.ini
35
35
36 - This command runs the rhodecode server the app should be available at the
36 - This command runs the rhodecode server the app should be available at the
37 127.0.0.1:5000. This ip and port is configurable via the production.ini
37 127.0.0.1:5000. This ip and port is configurable via the production.ini
38 file created in previous step
38 file created in previous step
39 - Use admin account you created to login.
39 - Use admin account you created to login.
40 - Default permissions on each repository is read, and owner is admin. So
40 - Default permissions on each repository is read, and owner is admin. So
41 remember to update these if needed.
41 remember to update these if needed.
42
42
43
43
44 Setting up Whoosh
44 Setting up Whoosh full text search
45 -----------------
45 ----------------------------------
46
47 Index for whoosh can be build starting from version 1.1 using paster command
48 passing repo locations to index, as well as Your config file that stores
49 whoosh index files locations. There is possible to pass `-f` to the options
50 to enable full index rebuild. Without that indexing will run always in in
51 incremental mode.
52
53 ::
54 paster make-index --repo-location=<location for repos> production.ini
55
56 for full index rebuild You can use
57
58 ::
59 paster make-index -f --repo-location=<location for repos> production.ini
46
60
47 - For full text search You can either put crontab entry for
61 - For full text search You can either put crontab entry for
48
62
63 This command can be run even from crontab in order to do periodical
64 index builds and keep Your index always up to date. An example entry might
65 look like this
66
49 ::
67 ::
50
68
51 python /var/www/rhodecode/<rhodecode_installation_path>/lib/indexers/daemon.py incremental <put_here_path_to_repos>
69 /path/to/python/bin/paster --repo-location=<location for repos> /path/to/rhodecode/production.ini
52
70
53 When using incremental mode whoosh will check last modification date of each file
71 When using incremental(default) mode whoosh will check last modification date
54 and add it to reindex if newer file is available. Also indexing daemon checks
72 of each file and add it to reindex if newer file is available. Also indexing
55 for removed files and removes them from index. Sometime You might want to rebuild
73 daemon checks for removed files and removes them from index.
56 index from scrach, in admin pannel You can check `build from scratch` flag
74
57 and in standalone daemon You can pass `full` instead on incremental to build
75 Sometime You might want to rebuild index from scratch. You can do that using
58 remove previos index and build new one.
76 the `-f` flag passed to paster command or, in admin panel You can check
77 `build from scratch` flag.
59
78
60 Nginx virtual host example
79 Nginx virtual host example
61 --------------------------
80 --------------------------
62
81
63 Sample config for nginx::
82 Sample config for nginx::
64
83
65 server {
84 server {
66 listen 80;
85 listen 80;
67 server_name hg.myserver.com;
86 server_name hg.myserver.com;
68 access_log /var/log/nginx/rhodecode.access.log;
87 access_log /var/log/nginx/rhodecode.access.log;
69 error_log /var/log/nginx/rhodecode.error.log;
88 error_log /var/log/nginx/rhodecode.error.log;
70 location / {
89 location / {
71 root /var/www/rhodecode/rhodecode/public/;
90 root /var/www/rhodecode/rhodecode/public/;
72 if (!-f $request_filename){
91 if (!-f $request_filename){
73 proxy_pass http://127.0.0.1:5000;
92 proxy_pass http://127.0.0.1:5000;
74 }
93 }
75 #this is important for https !!!
94 #this is important for https !!!
76 proxy_set_header X-Url-Scheme $scheme;
95 proxy_set_header X-Url-Scheme $scheme;
77 include /etc/nginx/proxy.conf;
96 include /etc/nginx/proxy.conf;
78 }
97 }
79 }
98 }
80
99
81 Here's the proxy.conf. It's tuned so it'll not timeout on long
100 Here's the proxy.conf. It's tuned so it'll not timeout on long
82 pushes and also on large pushes::
101 pushes and also on large pushes::
83
102
84 proxy_redirect off;
103 proxy_redirect off;
85 proxy_set_header Host $host;
104 proxy_set_header Host $host;
86 proxy_set_header X-Host $http_host;
105 proxy_set_header X-Host $http_host;
87 proxy_set_header X-Real-IP $remote_addr;
106 proxy_set_header X-Real-IP $remote_addr;
88 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
107 proxy_set_header X-Forwarded-For $proxy_add_x_forwarded_for;
89 proxy_set_header Proxy-host $proxy_host;
108 proxy_set_header Proxy-host $proxy_host;
90 client_max_body_size 400m;
109 client_max_body_size 400m;
91 client_body_buffer_size 128k;
110 client_body_buffer_size 128k;
92 proxy_buffering off;
111 proxy_buffering off;
93 proxy_connect_timeout 3600;
112 proxy_connect_timeout 3600;
94 proxy_send_timeout 3600;
113 proxy_send_timeout 3600;
95 proxy_read_timeout 3600;
114 proxy_read_timeout 3600;
96 proxy_buffer_size 8k;
115 proxy_buffer_size 8k;
97 proxy_buffers 8 32k;
116 proxy_buffers 8 32k;
98 proxy_busy_buffers_size 64k;
117 proxy_busy_buffers_size 64k;
99 proxy_temp_file_write_size 64k;
118 proxy_temp_file_write_size 64k;
100
119
101 Also when using root path with nginx You might set the static files to false
120 Also when using root path with nginx You might set the static files to false
102 in production.ini file::
121 in production.ini file::
103
122
104 [app:main]
123 [app:main]
105 use = egg:rhodecode
124 use = egg:rhodecode
106 full_stack = true
125 full_stack = true
107 static_files = false
126 static_files = false
108 lang=en
127 lang=en
109 cache_dir = %(here)s/data
128 cache_dir = %(here)s/data
110
129
111 To not have the statics served by the application. And improve speed.
130 To not have the statics served by the application. And improve speed.
112
131
113
132
114 Other configuration files
133 Other configuration files
115 -------------------------
134 -------------------------
116
135
117 Some extra configuration files and examples can be found here:
136 Some extra configuration files and examples can be found here:
118 http://hg.python-works.com/rhodecode/files/tip/init.d
137 http://hg.python-works.com/rhodecode/files/tip/init.d
119
138
120 and also an celeryconfig file can be use from here:
139 and also an celeryconfig file can be use from here:
121 http://hg.python-works.com/rhodecode/files/tip/celeryconfig.py
140 http://hg.python-works.com/rhodecode/files/tip/celeryconfig.py
122
141
123
142
124
143
125 .. _virtualenv: http://pypi.python.org/pypi/virtualenv
144 .. _virtualenv: http://pypi.python.org/pypi/virtualenv
126 .. _python: http://www.python.org/
145 .. _python: http://www.python.org/
127 .. _mercurial: http://mercurial.selenic.com/
146 .. _mercurial: http://mercurial.selenic.com/
128 .. _celery: http://celeryproject.org/
147 .. _celery: http://celeryproject.org/
129 .. _rabbitmq: http://www.rabbitmq.com/ No newline at end of file
148 .. _rabbitmq: http://www.rabbitmq.com/
@@ -1,174 +1,175 b''
1 ################################################################################
1 ################################################################################
2 ################################################################################
2 ################################################################################
3 # rhodecode - Pylons environment configuration #
3 # rhodecode - Pylons environment configuration #
4 # #
4 # #
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 ## Uncomment and replace with the address which should receive ##
11 ## Uncomment and replace with the address which should receive ##
12 ## any error reports after application crash ##
12 ## any error reports after application crash ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
14 ################################################################################
14 ################################################################################
15 #email_to = admin@localhost
15 #email_to = admin@localhost
16 #error_email_from = paste_error@localhost
16 #error_email_from = paste_error@localhost
17 #app_email_from = rhodecode-noreply@localhost
17 #app_email_from = rhodecode-noreply@localhost
18 #error_message =
18 #error_message =
19
19
20 #smtp_server = mail.server.com
20 #smtp_server = mail.server.com
21 #smtp_username =
21 #smtp_username =
22 #smtp_password =
22 #smtp_password =
23 #smtp_port =
23 #smtp_port =
24 #smtp_use_tls = false
24 #smtp_use_tls = false
25
25
26 [server:main]
26 [server:main]
27 ##nr of threads to spawn
27 ##nr of threads to spawn
28 threadpool_workers = 5
28 threadpool_workers = 5
29
29
30 ##max request before thread respawn
30 ##max request before thread respawn
31 threadpool_max_requests = 2
31 threadpool_max_requests = 2
32
32
33 ##option to use threads of process
33 ##option to use threads of process
34 use_threadpool = true
34 use_threadpool = true
35
35
36 use = egg:Paste#http
36 use = egg:Paste#http
37 host = 127.0.0.1
37 host = 127.0.0.1
38 port = 8001
38 port = 8001
39
39
40 [app:main]
40 [app:main]
41 use = egg:rhodecode
41 use = egg:rhodecode
42 full_stack = true
42 full_stack = true
43 static_files = false
43 static_files = false
44 lang=en
44 lang=en
45 cache_dir = %(here)s/data
45 cache_dir = %(here)s/data
46 index_dir = %(here)s/data/index
46
47
47 ####################################
48 ####################################
48 ### BEAKER CACHE ####
49 ### BEAKER CACHE ####
49 ####################################
50 ####################################
50 beaker.cache.data_dir=/%(here)s/data/cache/data
51 beaker.cache.data_dir=/%(here)s/data/cache/data
51 beaker.cache.lock_dir=/%(here)s/data/cache/lock
52 beaker.cache.lock_dir=/%(here)s/data/cache/lock
52 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
53 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
53
54
54 beaker.cache.super_short_term.type=memory
55 beaker.cache.super_short_term.type=memory
55 beaker.cache.super_short_term.expire=10
56 beaker.cache.super_short_term.expire=10
56
57
57 beaker.cache.short_term.type=memory
58 beaker.cache.short_term.type=memory
58 beaker.cache.short_term.expire=60
59 beaker.cache.short_term.expire=60
59
60
60 beaker.cache.long_term.type=memory
61 beaker.cache.long_term.type=memory
61 beaker.cache.long_term.expire=36000
62 beaker.cache.long_term.expire=36000
62
63
63
64
64 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.expire=5
66 beaker.cache.sql_cache_short.expire=5
66
67
67 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.expire=360
69 beaker.cache.sql_cache_med.expire=360
69
70
70 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.expire=3600
72 beaker.cache.sql_cache_long.expire=3600
72
73
73 ####################################
74 ####################################
74 ### BEAKER SESSION ####
75 ### BEAKER SESSION ####
75 ####################################
76 ####################################
76 ## Type of storage used for the session, current types are
77 ## Type of storage used for the session, current types are
77 ## dbm, file, memcached, database, and memory.
78 ## dbm, file, memcached, database, and memory.
78 ## The storage uses the Container API
79 ## The storage uses the Container API
79 ##that is also used by the cache system.
80 ##that is also used by the cache system.
80 beaker.session.type = file
81 beaker.session.type = file
81
82
82 beaker.session.key = rhodecode
83 beaker.session.key = rhodecode
83 beaker.session.secret = g654dcno0-9873jhgfreyu
84 beaker.session.secret = g654dcno0-9873jhgfreyu
84 beaker.session.timeout = 36000
85 beaker.session.timeout = 36000
85
86
86 ##auto save the session to not to use .save()
87 ##auto save the session to not to use .save()
87 beaker.session.auto = False
88 beaker.session.auto = False
88
89
89 ##true exire at browser close
90 ##true exire at browser close
90 #beaker.session.cookie_expires = 3600
91 #beaker.session.cookie_expires = 3600
91
92
92
93
93 ################################################################################
94 ################################################################################
94 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## execute malicious code after an exception is raised. ##
97 ## execute malicious code after an exception is raised. ##
97 ################################################################################
98 ################################################################################
98 set debug = false
99 set debug = false
99
100
100 ##################################
101 ##################################
101 ### LOGVIEW CONFIG ###
102 ### LOGVIEW CONFIG ###
102 ##################################
103 ##################################
103 logview.sqlalchemy = #faa
104 logview.sqlalchemy = #faa
104 logview.pylons.templating = #bfb
105 logview.pylons.templating = #bfb
105 logview.pylons.util = #eee
106 logview.pylons.util = #eee
106
107
107 #########################################################
108 #########################################################
108 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 #########################################################
110 #########################################################
110 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.pool_recycle = 3600
113 #sqlalchemy.db1.pool_recycle = 3600
113 sqlalchemy.convert_unicode = true
114 sqlalchemy.convert_unicode = true
114
115
115 ################################
116 ################################
116 ### LOGGING CONFIGURATION ####
117 ### LOGGING CONFIGURATION ####
117 ################################
118 ################################
118 [loggers]
119 [loggers]
119 keys = root, routes, rhodecode, sqlalchemy
120 keys = root, routes, rhodecode, sqlalchemy
120
121
121 [handlers]
122 [handlers]
122 keys = console
123 keys = console
123
124
124 [formatters]
125 [formatters]
125 keys = generic,color_formatter
126 keys = generic,color_formatter
126
127
127 #############
128 #############
128 ## LOGGERS ##
129 ## LOGGERS ##
129 #############
130 #############
130 [logger_root]
131 [logger_root]
131 level = INFO
132 level = INFO
132 handlers = console
133 handlers = console
133
134
134 [logger_routes]
135 [logger_routes]
135 level = INFO
136 level = INFO
136 handlers = console
137 handlers = console
137 qualname = routes.middleware
138 qualname = routes.middleware
138 # "level = DEBUG" logs the route matched and routing variables.
139 # "level = DEBUG" logs the route matched and routing variables.
139 propagate = 0
140 propagate = 0
140
141
141 [logger_rhodecode]
142 [logger_rhodecode]
142 level = DEBUG
143 level = DEBUG
143 handlers = console
144 handlers = console
144 qualname = rhodecode
145 qualname = rhodecode
145 propagate = 0
146 propagate = 0
146
147
147 [logger_sqlalchemy]
148 [logger_sqlalchemy]
148 level = ERROR
149 level = ERROR
149 handlers = console
150 handlers = console
150 qualname = sqlalchemy.engine
151 qualname = sqlalchemy.engine
151 propagate = 0
152 propagate = 0
152
153
153 ##############
154 ##############
154 ## HANDLERS ##
155 ## HANDLERS ##
155 ##############
156 ##############
156
157
157 [handler_console]
158 [handler_console]
158 class = StreamHandler
159 class = StreamHandler
159 args = (sys.stderr,)
160 args = (sys.stderr,)
160 level = NOTSET
161 level = NOTSET
161 formatter = color_formatter
162 formatter = color_formatter
162
163
163 ################
164 ################
164 ## FORMATTERS ##
165 ## FORMATTERS ##
165 ################
166 ################
166
167
167 [formatter_generic]
168 [formatter_generic]
168 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 datefmt = %Y-%m-%d %H:%M:%S
170 datefmt = %Y-%m-%d %H:%M:%S
170
171
171 [formatter_color_formatter]
172 [formatter_color_formatter]
172 class=rhodecode.lib.colored_formatter.ColorFormatter
173 class=rhodecode.lib.colored_formatter.ColorFormatter
173 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 datefmt = %Y-%m-%d %H:%M:%S No newline at end of file
175 datefmt = %Y-%m-%d %H:%M:%S
@@ -1,174 +1,175 b''
1 ################################################################################
1 ################################################################################
2 ################################################################################
2 ################################################################################
3 # rhodecode - Pylons environment configuration #
3 # rhodecode - Pylons environment configuration #
4 # #
4 # #
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 ## Uncomment and replace with the address which should receive ##
11 ## Uncomment and replace with the address which should receive ##
12 ## any error reports after application crash ##
12 ## any error reports after application crash ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
13 ## Additionally those settings will be used by rhodecode mailing system ##
14 ################################################################################
14 ################################################################################
15 #email_to = admin@localhost
15 #email_to = admin@localhost
16 #error_email_from = paste_error@localhost
16 #error_email_from = paste_error@localhost
17 #app_email_from = rhodecode-noreply@localhost
17 #app_email_from = rhodecode-noreply@localhost
18 #error_message =
18 #error_message =
19
19
20 #smtp_server = mail.server.com
20 #smtp_server = mail.server.com
21 #smtp_username =
21 #smtp_username =
22 #smtp_password =
22 #smtp_password =
23 #smtp_port =
23 #smtp_port =
24 #smtp_use_tls = false
24 #smtp_use_tls = false
25
25
26 [server:main]
26 [server:main]
27 ##nr of threads to spawn
27 ##nr of threads to spawn
28 threadpool_workers = 5
28 threadpool_workers = 5
29
29
30 ##max request before thread respawn
30 ##max request before thread respawn
31 threadpool_max_requests = 10
31 threadpool_max_requests = 10
32
32
33 ##option to use threads of process
33 ##option to use threads of process
34 use_threadpool = true
34 use_threadpool = true
35
35
36 use = egg:Paste#http
36 use = egg:Paste#http
37 host = 127.0.0.1
37 host = 127.0.0.1
38 port = 5000
38 port = 5000
39
39
40 [app:main]
40 [app:main]
41 use = egg:rhodecode
41 use = egg:rhodecode
42 full_stack = true
42 full_stack = true
43 static_files = true
43 static_files = true
44 lang=en
44 lang=en
45 cache_dir = %(here)s/data
45 cache_dir = %(here)s/data
46 index_dir = %(here)s/data/index
46 app_instance_uuid = ${app_instance_uuid}
47 app_instance_uuid = ${app_instance_uuid}
47
48
48 ####################################
49 ####################################
49 ### BEAKER CACHE ####
50 ### BEAKER CACHE ####
50 ####################################
51 ####################################
51 beaker.cache.data_dir=/%(here)s/data/cache/data
52 beaker.cache.data_dir=/%(here)s/data/cache/data
52 beaker.cache.lock_dir=/%(here)s/data/cache/lock
53 beaker.cache.lock_dir=/%(here)s/data/cache/lock
53 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
54 beaker.cache.regions=super_short_term,short_term,long_term,sql_cache_short,sql_cache_med,sql_cache_long
54
55
55 beaker.cache.super_short_term.type=memory
56 beaker.cache.super_short_term.type=memory
56 beaker.cache.super_short_term.expire=10
57 beaker.cache.super_short_term.expire=10
57
58
58 beaker.cache.short_term.type=memory
59 beaker.cache.short_term.type=memory
59 beaker.cache.short_term.expire=60
60 beaker.cache.short_term.expire=60
60
61
61 beaker.cache.long_term.type=memory
62 beaker.cache.long_term.type=memory
62 beaker.cache.long_term.expire=36000
63 beaker.cache.long_term.expire=36000
63
64
64 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.type=memory
65 beaker.cache.sql_cache_short.expire=5
66 beaker.cache.sql_cache_short.expire=5
66
67
67 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.type=memory
68 beaker.cache.sql_cache_med.expire=360
69 beaker.cache.sql_cache_med.expire=360
69
70
70 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.type=file
71 beaker.cache.sql_cache_long.expire=3600
72 beaker.cache.sql_cache_long.expire=3600
72
73
73 ####################################
74 ####################################
74 ### BEAKER SESSION ####
75 ### BEAKER SESSION ####
75 ####################################
76 ####################################
76 ## Type of storage used for the session, current types are
77 ## Type of storage used for the session, current types are
77 ## dbm, file, memcached, database, and memory.
78 ## dbm, file, memcached, database, and memory.
78 ## The storage uses the Container API
79 ## The storage uses the Container API
79 ##that is also used by the cache system.
80 ##that is also used by the cache system.
80 beaker.session.type = file
81 beaker.session.type = file
81
82
82 beaker.session.key = rhodecode
83 beaker.session.key = rhodecode
83 beaker.session.secret = ${app_instance_secret}
84 beaker.session.secret = ${app_instance_secret}
84 beaker.session.timeout = 36000
85 beaker.session.timeout = 36000
85
86
86 ##auto save the session to not to use .save()
87 ##auto save the session to not to use .save()
87 beaker.session.auto = False
88 beaker.session.auto = False
88
89
89 ##true exire at browser close
90 ##true exire at browser close
90 #beaker.session.cookie_expires = 3600
91 #beaker.session.cookie_expires = 3600
91
92
92
93
93 ################################################################################
94 ################################################################################
94 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## WARNING: *THE LINE BELOW MUST BE UNCOMMENTED ON A PRODUCTION ENVIRONMENT* ##
95 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## Debug mode will enable the interactive debugging tool, allowing ANYONE to ##
96 ## execute malicious code after an exception is raised. ##
97 ## execute malicious code after an exception is raised. ##
97 ################################################################################
98 ################################################################################
98 set debug = false
99 set debug = false
99
100
100 ##################################
101 ##################################
101 ### LOGVIEW CONFIG ###
102 ### LOGVIEW CONFIG ###
102 ##################################
103 ##################################
103 logview.sqlalchemy = #faa
104 logview.sqlalchemy = #faa
104 logview.pylons.templating = #bfb
105 logview.pylons.templating = #bfb
105 logview.pylons.util = #eee
106 logview.pylons.util = #eee
106
107
107 #########################################################
108 #########################################################
108 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 ### DB CONFIGS - EACH DB WILL HAVE IT'S OWN CONFIG ###
109 #########################################################
110 #########################################################
110 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 sqlalchemy.db1.url = sqlite:///%(here)s/rhodecode.db
111 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.echo = False
112 #sqlalchemy.db1.pool_recycle = 3600
113 #sqlalchemy.db1.pool_recycle = 3600
113 sqlalchemy.convert_unicode = true
114 sqlalchemy.convert_unicode = true
114
115
115 ################################
116 ################################
116 ### LOGGING CONFIGURATION ####
117 ### LOGGING CONFIGURATION ####
117 ################################
118 ################################
118 [loggers]
119 [loggers]
119 keys = root, routes, rhodecode, sqlalchemy
120 keys = root, routes, rhodecode, sqlalchemy
120
121
121 [handlers]
122 [handlers]
122 keys = console
123 keys = console
123
124
124 [formatters]
125 [formatters]
125 keys = generic,color_formatter
126 keys = generic,color_formatter
126
127
127 #############
128 #############
128 ## LOGGERS ##
129 ## LOGGERS ##
129 #############
130 #############
130 [logger_root]
131 [logger_root]
131 level = INFO
132 level = INFO
132 handlers = console
133 handlers = console
133
134
134 [logger_routes]
135 [logger_routes]
135 level = INFO
136 level = INFO
136 handlers = console
137 handlers = console
137 qualname = routes.middleware
138 qualname = routes.middleware
138 # "level = DEBUG" logs the route matched and routing variables.
139 # "level = DEBUG" logs the route matched and routing variables.
139 propagate = 0
140 propagate = 0
140
141
141 [logger_rhodecode]
142 [logger_rhodecode]
142 level = DEBUG
143 level = DEBUG
143 handlers = console
144 handlers = console
144 qualname = rhodecode
145 qualname = rhodecode
145 propagate = 0
146 propagate = 0
146
147
147 [logger_sqlalchemy]
148 [logger_sqlalchemy]
148 level = ERROR
149 level = ERROR
149 handlers = console
150 handlers = console
150 qualname = sqlalchemy.engine
151 qualname = sqlalchemy.engine
151 propagate = 0
152 propagate = 0
152
153
153 ##############
154 ##############
154 ## HANDLERS ##
155 ## HANDLERS ##
155 ##############
156 ##############
156
157
157 [handler_console]
158 [handler_console]
158 class = StreamHandler
159 class = StreamHandler
159 args = (sys.stderr,)
160 args = (sys.stderr,)
160 level = NOTSET
161 level = NOTSET
161 formatter = color_formatter
162 formatter = color_formatter
162
163
163 ################
164 ################
164 ## FORMATTERS ##
165 ## FORMATTERS ##
165 ################
166 ################
166
167
167 [formatter_generic]
168 [formatter_generic]
168 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 format = %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
169 datefmt = %Y-%m-%d %H:%M:%S
170 datefmt = %Y-%m-%d %H:%M:%S
170
171
171 [formatter_color_formatter]
172 [formatter_color_formatter]
172 class=rhodecode.lib.colored_formatter.ColorFormatter
173 class=rhodecode.lib.colored_formatter.ColorFormatter
173 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 format= %(asctime)s.%(msecs)03d %(levelname)-5.5s [%(name)s] %(message)s
174 datefmt = %Y-%m-%d %H:%M:%S No newline at end of file
175 datefmt = %Y-%m-%d %H:%M:%S
@@ -1,196 +1,192 b''
1 import os
1 import os
2 import sys
2 import sys
3 from os.path import dirname as dn, join as jn
3 from os.path import dirname as dn, join as jn
4
4
5 #to get the rhodecode import
5 #to get the rhodecode import
6 sys.path.append(dn(dn(dn(os.path.realpath(__file__)))))
6 sys.path.append(dn(dn(dn(os.path.realpath(__file__)))))
7
7
8 from rhodecode.config.environment import load_environment
8 from rhodecode.config.environment import load_environment
9 from rhodecode.model.hg import HgModel
9 from rhodecode.model.hg import HgModel
10 from shutil import rmtree
10 from shutil import rmtree
11 from webhelpers.html.builder import escape
11 from webhelpers.html.builder import escape
12 from vcs.utils.lazy import LazyProperty
12 from vcs.utils.lazy import LazyProperty
13
13
14 from whoosh.analysis import RegexTokenizer, LowercaseFilter, StopFilter
14 from whoosh.analysis import RegexTokenizer, LowercaseFilter, StopFilter
15 from whoosh.fields import TEXT, ID, STORED, Schema, FieldType
15 from whoosh.fields import TEXT, ID, STORED, Schema, FieldType
16 from whoosh.index import create_in, open_dir
16 from whoosh.index import create_in, open_dir
17 from whoosh.formats import Characters
17 from whoosh.formats import Characters
18 from whoosh.highlight import highlight, SimpleFragmenter, HtmlFormatter
18 from whoosh.highlight import highlight, SimpleFragmenter, HtmlFormatter
19
19
20 import traceback
20 import traceback
21
21
22
22
23 #LOCATION WE KEEP THE INDEX
23 #LOCATION WE KEEP THE INDEX
24 IDX_LOCATION = jn(dn(dn(dn(dn(os.path.abspath(__file__))))), 'data', 'index')
24 IDX_LOCATION = jn(dn(dn(dn(dn(os.path.abspath(__file__))))), 'data', 'index')
25
25
26 #EXTENSIONS WE WANT TO INDEX CONTENT OFF
26 #EXTENSIONS WE WANT TO INDEX CONTENT OFF
27 INDEX_EXTENSIONS = ['action', 'adp', 'ashx', 'asmx', 'aspx', 'asx', 'axd', 'c',
27 INDEX_EXTENSIONS = ['action', 'adp', 'ashx', 'asmx', 'aspx', 'asx', 'axd', 'c',
28 'cfg', 'cfm', 'cpp', 'cs', 'css', 'diff', 'do', 'el', 'erl',
28 'cfg', 'cfm', 'cpp', 'cs', 'css', 'diff', 'do', 'el', 'erl',
29 'h', 'htm', 'html', 'ini', 'java', 'js', 'jsp', 'jspx', 'lisp',
29 'h', 'htm', 'html', 'ini', 'java', 'js', 'jsp', 'jspx', 'lisp',
30 'lua', 'm', 'mako', 'ml', 'pas', 'patch', 'php', 'php3',
30 'lua', 'm', 'mako', 'ml', 'pas', 'patch', 'php', 'php3',
31 'php4', 'phtml', 'pm', 'py', 'rb', 'rst', 's', 'sh', 'sql',
31 'php4', 'phtml', 'pm', 'py', 'rb', 'rst', 's', 'sh', 'sql',
32 'tpl', 'txt', 'vim', 'wss', 'xhtml', 'xml', 'xsl', 'xslt',
32 'tpl', 'txt', 'vim', 'wss', 'xhtml', 'xml', 'xsl', 'xslt',
33 'yaws']
33 'yaws']
34
34
35 #CUSTOM ANALYZER wordsplit + lowercase filter
35 #CUSTOM ANALYZER wordsplit + lowercase filter
36 ANALYZER = RegexTokenizer(expression=r"\w+") | LowercaseFilter()
36 ANALYZER = RegexTokenizer(expression=r"\w+") | LowercaseFilter()
37
37
38
38
39 #INDEX SCHEMA DEFINITION
39 #INDEX SCHEMA DEFINITION
40 SCHEMA = Schema(owner=TEXT(),
40 SCHEMA = Schema(owner=TEXT(),
41 repository=TEXT(stored=True),
41 repository=TEXT(stored=True),
42 path=TEXT(stored=True),
42 path=TEXT(stored=True),
43 content=FieldType(format=Characters(ANALYZER),
43 content=FieldType(format=Characters(ANALYZER),
44 scorable=True, stored=True),
44 scorable=True, stored=True),
45 modtime=STORED(), extension=TEXT(stored=True))
45 modtime=STORED(), extension=TEXT(stored=True))
46
46
47
47
48 IDX_NAME = 'HG_INDEX'
48 IDX_NAME = 'HG_INDEX'
49 FORMATTER = HtmlFormatter('span', between='\n<span class="break">...</span>\n')
49 FORMATTER = HtmlFormatter('span', between='\n<span class="break">...</span>\n')
50 FRAGMENTER = SimpleFragmenter(200)
50 FRAGMENTER = SimpleFragmenter(200)
51
51
52 from paste.script import command
52 from paste.script import command
53 import ConfigParser
53 import ConfigParser
54
54
55 class MakeIndex(command.Command):
55 class MakeIndex(command.Command):
56
56
57 max_args = 1
57 max_args = 1
58 min_args = 1
58 min_args = 1
59
59
60 usage = "CONFIG_FILE"
60 usage = "CONFIG_FILE"
61 summary = "Creates index for full text search given configuration file"
61 summary = "Creates index for full text search given configuration file"
62 group_name = "Whoosh indexing"
62 group_name = "RhodeCode"
63
63 takes_config_file = -1
64 parser = command.Command.standard_parser(verbose=True)
64 parser = command.Command.standard_parser(verbose=True)
65 # parser.add_option('--repo-location',
65 parser.add_option('--repo-location',
66 # action='store',
66 action='store',
67 # dest='repo_location',
67 dest='repo_location',
68 # help="Specifies repositories location to index",
68 help="Specifies repositories location to index REQUIRED",
69 # )
69 )
70 parser.add_option('-f',
70 parser.add_option('-f',
71 action='store_true',
71 action='store_true',
72 dest='full_index',
72 dest='full_index',
73 help="Specifies that index should be made full i.e"
73 help="Specifies that index should be made full i.e"
74 " destroy old and build from scratch",
74 " destroy old and build from scratch",
75 default=False)
75 default=False)
76 def command(self):
76 def command(self):
77 config_name = self.args[0]
77 config_name = self.args[0]
78
79 p = config_name.split('/')
78 p = config_name.split('/')
80 if len(p) == 1:
79 root = '.' if len(p) == 1 else '/'.join(p[:-1])
81 root = '.'
82 else:
83 root = '/'.join(p[:-1])
84 print root
85 config = ConfigParser.ConfigParser({'here':root})
80 config = ConfigParser.ConfigParser({'here':root})
86 config.read(config_name)
81 config.read(config_name)
87 print dict(config.items('app:main'))['index_dir']
82
88 index_location = dict(config.items('app:main'))['index_dir']
83 index_location = dict(config.items('app:main'))['index_dir']
89 #return
84 repo_location = self.options.repo_location
90
85
91 #=======================================================================
86 #======================================================================
92 # WHOOSH DAEMON
87 # WHOOSH DAEMON
93 #=======================================================================
88 #======================================================================
94 from rhodecode.lib.pidlock import LockHeld, DaemonLock
89 from rhodecode.lib.pidlock import LockHeld, DaemonLock
95 from rhodecode.lib.indexers.daemon import WhooshIndexingDaemon
90 from rhodecode.lib.indexers.daemon import WhooshIndexingDaemon
96 try:
91 try:
97 l = DaemonLock()
92 l = DaemonLock()
98 WhooshIndexingDaemon(index_location=index_location)\
93 WhooshIndexingDaemon(index_location=index_location,
94 repo_location=repo_location)\
99 .run(full_index=self.options.full_index)
95 .run(full_index=self.options.full_index)
100 l.release()
96 l.release()
101 except LockHeld:
97 except LockHeld:
102 sys.exit(1)
98 sys.exit(1)
103
99
104
100
105 class ResultWrapper(object):
101 class ResultWrapper(object):
106 def __init__(self, search_type, searcher, matcher, highlight_items):
102 def __init__(self, search_type, searcher, matcher, highlight_items):
107 self.search_type = search_type
103 self.search_type = search_type
108 self.searcher = searcher
104 self.searcher = searcher
109 self.matcher = matcher
105 self.matcher = matcher
110 self.highlight_items = highlight_items
106 self.highlight_items = highlight_items
111 self.fragment_size = 200 / 2
107 self.fragment_size = 200 / 2
112
108
113 @LazyProperty
109 @LazyProperty
114 def doc_ids(self):
110 def doc_ids(self):
115 docs_id = []
111 docs_id = []
116 while self.matcher.is_active():
112 while self.matcher.is_active():
117 docnum = self.matcher.id()
113 docnum = self.matcher.id()
118 chunks = [offsets for offsets in self.get_chunks()]
114 chunks = [offsets for offsets in self.get_chunks()]
119 docs_id.append([docnum, chunks])
115 docs_id.append([docnum, chunks])
120 self.matcher.next()
116 self.matcher.next()
121 return docs_id
117 return docs_id
122
118
123 def __str__(self):
119 def __str__(self):
124 return '<%s at %s>' % (self.__class__.__name__, len(self.doc_ids))
120 return '<%s at %s>' % (self.__class__.__name__, len(self.doc_ids))
125
121
126 def __repr__(self):
122 def __repr__(self):
127 return self.__str__()
123 return self.__str__()
128
124
129 def __len__(self):
125 def __len__(self):
130 return len(self.doc_ids)
126 return len(self.doc_ids)
131
127
132 def __iter__(self):
128 def __iter__(self):
133 """
129 """
134 Allows Iteration over results,and lazy generate content
130 Allows Iteration over results,and lazy generate content
135
131
136 *Requires* implementation of ``__getitem__`` method.
132 *Requires* implementation of ``__getitem__`` method.
137 """
133 """
138 for docid in self.doc_ids:
134 for docid in self.doc_ids:
139 yield self.get_full_content(docid)
135 yield self.get_full_content(docid)
140
136
141 def __getslice__(self, i, j):
137 def __getslice__(self, i, j):
142 """
138 """
143 Slicing of resultWrapper
139 Slicing of resultWrapper
144 """
140 """
145 slice = []
141 slice = []
146 for docid in self.doc_ids[i:j]:
142 for docid in self.doc_ids[i:j]:
147 slice.append(self.get_full_content(docid))
143 slice.append(self.get_full_content(docid))
148 return slice
144 return slice
149
145
150
146
151 def get_full_content(self, docid):
147 def get_full_content(self, docid):
152 res = self.searcher.stored_fields(docid[0])
148 res = self.searcher.stored_fields(docid[0])
153 f_path = res['path'][res['path'].find(res['repository']) \
149 f_path = res['path'][res['path'].find(res['repository']) \
154 + len(res['repository']):].lstrip('/')
150 + len(res['repository']):].lstrip('/')
155
151
156 content_short = self.get_short_content(res, docid[1])
152 content_short = self.get_short_content(res, docid[1])
157 res.update({'content_short':content_short,
153 res.update({'content_short':content_short,
158 'content_short_hl':self.highlight(content_short),
154 'content_short_hl':self.highlight(content_short),
159 'f_path':f_path})
155 'f_path':f_path})
160
156
161 return res
157 return res
162
158
163 def get_short_content(self, res, chunks):
159 def get_short_content(self, res, chunks):
164
160
165 return ''.join([res['content'][chunk[0]:chunk[1]] for chunk in chunks])
161 return ''.join([res['content'][chunk[0]:chunk[1]] for chunk in chunks])
166
162
167 def get_chunks(self):
163 def get_chunks(self):
168 """
164 """
169 Smart function that implements chunking the content
165 Smart function that implements chunking the content
170 but not overlap chunks so it doesn't highlight the same
166 but not overlap chunks so it doesn't highlight the same
171 close occurrences twice.
167 close occurrences twice.
172 @param matcher:
168 @param matcher:
173 @param size:
169 @param size:
174 """
170 """
175 memory = [(0, 0)]
171 memory = [(0, 0)]
176 for span in self.matcher.spans():
172 for span in self.matcher.spans():
177 start = span.startchar or 0
173 start = span.startchar or 0
178 end = span.endchar or 0
174 end = span.endchar or 0
179 start_offseted = max(0, start - self.fragment_size)
175 start_offseted = max(0, start - self.fragment_size)
180 end_offseted = end + self.fragment_size
176 end_offseted = end + self.fragment_size
181
177
182 if start_offseted < memory[-1][1]:
178 if start_offseted < memory[-1][1]:
183 start_offseted = memory[-1][1]
179 start_offseted = memory[-1][1]
184 memory.append((start_offseted, end_offseted,))
180 memory.append((start_offseted, end_offseted,))
185 yield (start_offseted, end_offseted,)
181 yield (start_offseted, end_offseted,)
186
182
187 def highlight(self, content, top=5):
183 def highlight(self, content, top=5):
188 if self.search_type != 'content':
184 if self.search_type != 'content':
189 return ''
185 return ''
190 hl = highlight(escape(content),
186 hl = highlight(escape(content),
191 self.highlight_items,
187 self.highlight_items,
192 analyzer=ANALYZER,
188 analyzer=ANALYZER,
193 fragmenter=FRAGMENTER,
189 fragmenter=FRAGMENTER,
194 formatter=FORMATTER,
190 formatter=FORMATTER,
195 top=top)
191 top=top)
196 return hl
192 return hl
@@ -1,217 +1,215 b''
1 #!/usr/bin/env python
1 #!/usr/bin/env python
2 # encoding: utf-8
2 # encoding: utf-8
3 # whoosh indexer daemon for rhodecode
3 # whoosh indexer daemon for rhodecode
4 # Copyright (C) 2009-2010 Marcin Kuzminski <marcin@python-works.com>
4 # Copyright (C) 2009-2010 Marcin Kuzminski <marcin@python-works.com>
5 #
5 #
6 # This program is free software; you can redistribute it and/or
6 # This program is free software; you can redistribute it and/or
7 # modify it under the terms of the GNU General Public License
7 # modify it under the terms of the GNU General Public License
8 # as published by the Free Software Foundation; version 2
8 # as published by the Free Software Foundation; version 2
9 # of the License or (at your opinion) any later version of the license.
9 # of the License or (at your opinion) any later version of the license.
10 #
10 #
11 # This program is distributed in the hope that it will be useful,
11 # This program is distributed in the hope that it will be useful,
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
12 # but WITHOUT ANY WARRANTY; without even the implied warranty of
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 # MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
14 # GNU General Public License for more details.
14 # GNU General Public License for more details.
15 #
15 #
16 # You should have received a copy of the GNU General Public License
16 # You should have received a copy of the GNU General Public License
17 # along with this program; if not, write to the Free Software
17 # along with this program; if not, write to the Free Software
18 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
18 # Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston,
19 # MA 02110-1301, USA.
19 # MA 02110-1301, USA.
20 """
20 """
21 Created on Jan 26, 2010
21 Created on Jan 26, 2010
22
22
23 @author: marcink
23 @author: marcink
24 A deamon will read from task table and run tasks
24 A deamon will read from task table and run tasks
25 """
25 """
26 import sys
26 import sys
27 import os
27 import os
28 from os.path import dirname as dn
28 from os.path import dirname as dn
29 from os.path import join as jn
29 from os.path import join as jn
30
30
31 #to get the rhodecode import
31 #to get the rhodecode import
32 project_path = dn(dn(dn(dn(os.path.realpath(__file__)))))
32 project_path = dn(dn(dn(dn(os.path.realpath(__file__)))))
33 sys.path.append(project_path)
33 sys.path.append(project_path)
34
34
35
35
36 from rhodecode.model.hg import HgModel
36 from rhodecode.model.hg import HgModel
37 from rhodecode.lib.helpers import safe_unicode
37 from rhodecode.lib.helpers import safe_unicode
38 from whoosh.index import create_in, open_dir
38 from whoosh.index import create_in, open_dir
39 from shutil import rmtree
39 from shutil import rmtree
40 from rhodecode.lib.indexers import INDEX_EXTENSIONS, SCHEMA, IDX_NAME
40 from rhodecode.lib.indexers import INDEX_EXTENSIONS, SCHEMA, IDX_NAME
41
41
42 from time import mktime
42 from time import mktime
43 from vcs.exceptions import ChangesetError, RepositoryError
43 from vcs.exceptions import ChangesetError, RepositoryError
44
44
45 import logging
45 import logging
46
46
47 log = logging.getLogger('whooshIndexer')
47 log = logging.getLogger('whooshIndexer')
48 # create logger
48 # create logger
49 log.setLevel(logging.DEBUG)
49 log.setLevel(logging.DEBUG)
50 log.propagate = False
50 log.propagate = False
51 # create console handler and set level to debug
51 # create console handler and set level to debug
52 ch = logging.StreamHandler()
52 ch = logging.StreamHandler()
53 ch.setLevel(logging.DEBUG)
53 ch.setLevel(logging.DEBUG)
54
54
55 # create formatter
55 # create formatter
56 formatter = logging.Formatter("%(asctime)s - %(name)s - %(levelname)s - %(message)s")
56 formatter = logging.Formatter("%(asctime)s - %(name)s - %(levelname)s - %(message)s")
57
57
58 # add formatter to ch
58 # add formatter to ch
59 ch.setFormatter(formatter)
59 ch.setFormatter(formatter)
60
60
61 # add ch to logger
61 # add ch to logger
62 log.addHandler(ch)
62 log.addHandler(ch)
63
63
64 class WhooshIndexingDaemon(object):
64 class WhooshIndexingDaemon(object):
65 """
65 """
66 Deamon for atomic jobs
66 Deamon for atomic jobs
67 """
67 """
68
68
69 def __init__(self, indexname='HG_INDEX', index_location=None,
69 def __init__(self, indexname='HG_INDEX', index_location=None,
70 repo_location=None):
70 repo_location=None):
71 self.indexname = indexname
71 self.indexname = indexname
72
72
73 self.index_location = index_location
73 self.index_location = index_location
74 if not index_location:
74 if not index_location:
75 raise Exception('You have to provide index location')
75 raise Exception('You have to provide index location')
76
76
77 self.repo_location = repo_location
77 self.repo_location = repo_location
78 if not repo_location:
78 if not repo_location:
79 raise Exception('You have to provide repositories location')
79 raise Exception('You have to provide repositories location')
80
80
81
81 self.repo_paths = HgModel().repo_scan(self.repo_location, None, True)
82
83 self.repo_paths = HgModel.repo_scan('/', self.repo_location, None, True)
84 self.initial = False
82 self.initial = False
85 if not os.path.isdir(self.index_location):
83 if not os.path.isdir(self.index_location):
86 os.mkdir(self.index_location)
84 os.mkdir(self.index_location)
87 log.info('Cannot run incremental index since it does not'
85 log.info('Cannot run incremental index since it does not'
88 ' yet exist running full build')
86 ' yet exist running full build')
89 self.initial = True
87 self.initial = True
90
88
91 def get_paths(self, repo):
89 def get_paths(self, repo):
92 """
90 """recursive walk in root dir and return a set of all path in that dir
93 recursive walk in root dir and return a set of all path in that dir
94 based on repository walk function
91 based on repository walk function
95 """
92 """
96 index_paths_ = set()
93 index_paths_ = set()
97 try:
94 try:
98 for topnode, dirs, files in repo.walk('/', 'tip'):
95 for topnode, dirs, files in repo.walk('/', 'tip'):
99 for f in files:
96 for f in files:
100 index_paths_.add(jn(repo.path, f.path))
97 index_paths_.add(jn(repo.path, f.path))
101 for dir in dirs:
98 for dir in dirs:
102 for f in files:
99 for f in files:
103 index_paths_.add(jn(repo.path, f.path))
100 index_paths_.add(jn(repo.path, f.path))
104
101
105 except RepositoryError:
102 except RepositoryError:
106 pass
103 pass
107 return index_paths_
104 return index_paths_
108
105
109 def get_node(self, repo, path):
106 def get_node(self, repo, path):
110 n_path = path[len(repo.path) + 1:]
107 n_path = path[len(repo.path) + 1:]
111 node = repo.get_changeset().get_node(n_path)
108 node = repo.get_changeset().get_node(n_path)
112 return node
109 return node
113
110
114 def get_node_mtime(self, node):
111 def get_node_mtime(self, node):
115 return mktime(node.last_changeset.date.timetuple())
112 return mktime(node.last_changeset.date.timetuple())
116
113
117 def add_doc(self, writer, path, repo):
114 def add_doc(self, writer, path, repo):
118 """Adding doc to writer"""
115 """Adding doc to writer this function itself fetches data from
116 the instance of vcs backend"""
119 node = self.get_node(repo, path)
117 node = self.get_node(repo, path)
120
118
121 #we just index the content of chosen files
119 #we just index the content of chosen files
122 if node.extension in INDEX_EXTENSIONS:
120 if node.extension in INDEX_EXTENSIONS:
123 log.debug(' >> %s [WITH CONTENT]' % path)
121 log.debug(' >> %s [WITH CONTENT]' % path)
124 u_content = node.content
122 u_content = node.content
125 else:
123 else:
126 log.debug(' >> %s' % path)
124 log.debug(' >> %s' % path)
127 #just index file name without it's content
125 #just index file name without it's content
128 u_content = u''
126 u_content = u''
129
127
130 writer.add_document(owner=unicode(repo.contact),
128 writer.add_document(owner=unicode(repo.contact),
131 repository=safe_unicode(repo.name),
129 repository=safe_unicode(repo.name),
132 path=safe_unicode(path),
130 path=safe_unicode(path),
133 content=u_content,
131 content=u_content,
134 modtime=self.get_node_mtime(node),
132 modtime=self.get_node_mtime(node),
135 extension=node.extension)
133 extension=node.extension)
136
134
137
135
138 def build_index(self):
136 def build_index(self):
139 if os.path.exists(self.index_location):
137 if os.path.exists(self.index_location):
140 log.debug('removing previous index')
138 log.debug('removing previous index')
141 rmtree(self.index_location)
139 rmtree(self.index_location)
142
140
143 if not os.path.exists(self.index_location):
141 if not os.path.exists(self.index_location):
144 os.mkdir(self.index_location)
142 os.mkdir(self.index_location)
145
143
146 idx = create_in(self.index_location, SCHEMA, indexname=IDX_NAME)
144 idx = create_in(self.index_location, SCHEMA, indexname=IDX_NAME)
147 writer = idx.writer()
145 writer = idx.writer()
148
146
149 for cnt, repo in enumerate(self.repo_paths.values()):
147 for cnt, repo in enumerate(self.repo_paths.values()):
150 log.debug('building index @ %s' % repo.path)
148 log.debug('building index @ %s' % repo.path)
151
149
152 for idx_path in self.get_paths(repo):
150 for idx_path in self.get_paths(repo):
153 self.add_doc(writer, idx_path, repo)
151 self.add_doc(writer, idx_path, repo)
154
152
155 log.debug('>> COMMITING CHANGES <<')
153 log.debug('>> COMMITING CHANGES <<')
156 writer.commit(merge=True)
154 writer.commit(merge=True)
157 log.debug('>>> FINISHED BUILDING INDEX <<<')
155 log.debug('>>> FINISHED BUILDING INDEX <<<')
158
156
159
157
160 def update_index(self):
158 def update_index(self):
161 log.debug('STARTING INCREMENTAL INDEXING UPDATE')
159 log.debug('STARTING INCREMENTAL INDEXING UPDATE')
162
160
163 idx = open_dir(self.index_location, indexname=self.indexname)
161 idx = open_dir(self.index_location, indexname=self.indexname)
164 # The set of all paths in the index
162 # The set of all paths in the index
165 indexed_paths = set()
163 indexed_paths = set()
166 # The set of all paths we need to re-index
164 # The set of all paths we need to re-index
167 to_index = set()
165 to_index = set()
168
166
169 reader = idx.reader()
167 reader = idx.reader()
170 writer = idx.writer()
168 writer = idx.writer()
171
169
172 # Loop over the stored fields in the index
170 # Loop over the stored fields in the index
173 for fields in reader.all_stored_fields():
171 for fields in reader.all_stored_fields():
174 indexed_path = fields['path']
172 indexed_path = fields['path']
175 indexed_paths.add(indexed_path)
173 indexed_paths.add(indexed_path)
176
174
177 repo = self.repo_paths[fields['repository']]
175 repo = self.repo_paths[fields['repository']]
178
176
179 try:
177 try:
180 node = self.get_node(repo, indexed_path)
178 node = self.get_node(repo, indexed_path)
181 except ChangesetError:
179 except ChangesetError:
182 # This file was deleted since it was indexed
180 # This file was deleted since it was indexed
183 log.debug('removing from index %s' % indexed_path)
181 log.debug('removing from index %s' % indexed_path)
184 writer.delete_by_term('path', indexed_path)
182 writer.delete_by_term('path', indexed_path)
185
183
186 else:
184 else:
187 # Check if this file was changed since it was indexed
185 # Check if this file was changed since it was indexed
188 indexed_time = fields['modtime']
186 indexed_time = fields['modtime']
189 mtime = self.get_node_mtime(node)
187 mtime = self.get_node_mtime(node)
190 if mtime > indexed_time:
188 if mtime > indexed_time:
191 # The file has changed, delete it and add it to the list of
189 # The file has changed, delete it and add it to the list of
192 # files to reindex
190 # files to reindex
193 log.debug('adding to reindex list %s' % indexed_path)
191 log.debug('adding to reindex list %s' % indexed_path)
194 writer.delete_by_term('path', indexed_path)
192 writer.delete_by_term('path', indexed_path)
195 to_index.add(indexed_path)
193 to_index.add(indexed_path)
196
194
197 # Loop over the files in the filesystem
195 # Loop over the files in the filesystem
198 # Assume we have a function that gathers the filenames of the
196 # Assume we have a function that gathers the filenames of the
199 # documents to be indexed
197 # documents to be indexed
200 for repo in self.repo_paths.values():
198 for repo in self.repo_paths.values():
201 for path in self.get_paths(repo):
199 for path in self.get_paths(repo):
202 if path in to_index or path not in indexed_paths:
200 if path in to_index or path not in indexed_paths:
203 # This is either a file that's changed, or a new file
201 # This is either a file that's changed, or a new file
204 # that wasn't indexed before. So index it!
202 # that wasn't indexed before. So index it!
205 self.add_doc(writer, path, repo)
203 self.add_doc(writer, path, repo)
206 log.debug('re indexing %s' % path)
204 log.debug('re indexing %s' % path)
207
205
208 log.debug('>> COMMITING CHANGES <<')
206 log.debug('>> COMMITING CHANGES <<')
209 writer.commit(merge=True)
207 writer.commit(merge=True)
210 log.debug('>>> FINISHED REBUILDING INDEX <<<')
208 log.debug('>>> FINISHED REBUILDING INDEX <<<')
211
209
212 def run(self, full_index=False):
210 def run(self, full_index=False):
213 """Run daemon"""
211 """Run daemon"""
214 if full_index or self.initial:
212 if full_index or self.initial:
215 self.build_index()
213 self.build_index()
216 else:
214 else:
217 self.update_index()
215 self.update_index()
@@ -1,42 +1,42 b''
1 [egg_info]
1 [egg_info]
2 tag_build = rc4
2 tag_build = beta
3 tag_svn_revision = true
3 tag_svn_revision = true
4
4
5 [easy_install]
5 [easy_install]
6 find_links = http://www.pylonshq.com/download/
6 find_links = http://www.pylonshq.com/download/
7
7
8 [nosetests]
8 [nosetests]
9 verbose=True
9 verbose=True
10 verbosity=2
10 verbosity=2
11 with-pylons=test.ini
11 with-pylons=test.ini
12 detailed-errors=1
12 detailed-errors=1
13
13
14 # Babel configuration
14 # Babel configuration
15 [compile_catalog]
15 [compile_catalog]
16 domain = rhodecode
16 domain = rhodecode
17 directory = rhodecode/i18n
17 directory = rhodecode/i18n
18 statistics = true
18 statistics = true
19
19
20 [extract_messages]
20 [extract_messages]
21 add_comments = TRANSLATORS:
21 add_comments = TRANSLATORS:
22 output_file = rhodecode/i18n/rhodecode.pot
22 output_file = rhodecode/i18n/rhodecode.pot
23 width = 80
23 width = 80
24
24
25 [init_catalog]
25 [init_catalog]
26 domain = rhodecode
26 domain = rhodecode
27 input_file = rhodecode/i18n/rhodecode.pot
27 input_file = rhodecode/i18n/rhodecode.pot
28 output_dir = rhodecode/i18n
28 output_dir = rhodecode/i18n
29
29
30 [update_catalog]
30 [update_catalog]
31 domain = rhodecode
31 domain = rhodecode
32 input_file = rhodecode/i18n/rhodecode.pot
32 input_file = rhodecode/i18n/rhodecode.pot
33 output_dir = rhodecode/i18n
33 output_dir = rhodecode/i18n
34 previous = true
34 previous = true
35
35
36 [build_sphinx]
36 [build_sphinx]
37 source-dir = docs/
37 source-dir = docs/
38 build-dir = docs/_build
38 build-dir = docs/_build
39 all_files = 1
39 all_files = 1
40
40
41 [upload_sphinx]
41 [upload_sphinx]
42 upload-dir = docs/_build/html No newline at end of file
42 upload-dir = docs/_build/html
@@ -1,93 +1,98 b''
1 from rhodecode import get_version
1 from rhodecode import get_version
2 import sys
2 import sys
3 py_version = sys.version_info
3 py_version = sys.version_info
4
4
5 requirements = [
5 requirements = [
6 "Pylons>=1.0.0",
6 "Pylons>=1.0.0",
7 "SQLAlchemy>=0.6.5",
7 "SQLAlchemy>=0.6.5",
8 "Mako>=0.3.5",
8 "Mako>=0.3.5",
9 "vcs>=0.1.10",
9 "vcs>=0.1.10",
10 "pygments>=1.3.0",
10 "pygments>=1.3.0",
11 "mercurial>=1.6.4",
11 "mercurial>=1.6.4",
12 "whoosh>=1.3.1",
12 "whoosh>=1.3.1",
13 "celery>=2.1.3",
13 "celery>=2.1.3",
14 "py-bcrypt",
14 "py-bcrypt",
15 "babel",
15 "babel",
16 ]
16 ]
17
17
18 classifiers = ['Development Status :: 4 - Beta',
18 classifiers = ['Development Status :: 4 - Beta',
19 'Environment :: Web Environment',
19 'Environment :: Web Environment',
20 'Framework :: Pylons',
20 'Framework :: Pylons',
21 'Intended Audience :: Developers',
21 'Intended Audience :: Developers',
22 'License :: OSI Approved :: BSD License',
22 'License :: OSI Approved :: BSD License',
23 'Operating System :: OS Independent',
23 'Operating System :: OS Independent',
24 'Programming Language :: Python', ]
24 'Programming Language :: Python', ]
25
25
26 if sys.version_info < (2, 6):
26 if sys.version_info < (2, 6):
27 requirements.append("simplejson")
27 requirements.append("simplejson")
28 requirements.append("pysqlite")
28 requirements.append("pysqlite")
29
29
30 #additional files from project that goes somewhere in the filesystem
30 #additional files from project that goes somewhere in the filesystem
31 #relative to sys.prefix
31 #relative to sys.prefix
32 data_files = []
32 data_files = []
33
33
34 #additional files that goes into package itself
34 #additional files that goes into package itself
35 package_data = {'rhodecode': ['i18n/*/LC_MESSAGES/*.mo', ], }
35 package_data = {'rhodecode': ['i18n/*/LC_MESSAGES/*.mo', ], }
36
36
37 description = ('Mercurial and Git repository browser/management with '
37 description = ('Mercurial and Git repository browser/management with '
38 'build in push/pull server and full text search')
38 'build in push/pull server and full text search')
39 #long description
39 #long description
40 try:
40 try:
41 readme_file = 'README.rst'
41 readme_file = 'README.rst'
42 changelog_file = 'docs/changelog.rst'
42 changelog_file = 'docs/changelog.rst'
43 long_description = open(readme_file).read() + '/n/n' + \
43 long_description = open(readme_file).read() + '/n/n' + \
44 open(changelog_file).read()
44 open(changelog_file).read()
45
45
46 except IOError, err:
46 except IOError, err:
47 sys.stderr.write("[WARNING] Cannot find file specified as "
47 sys.stderr.write("[WARNING] Cannot find file specified as "
48 "long_description (%s)\n or changelog (%s) skipping that file" \
48 "long_description (%s)\n or changelog (%s) skipping that file" \
49 % (readme_file, changelog_file))
49 % (readme_file, changelog_file))
50 long_description = description
50 long_description = description
51
51
52
52
53 try:
53 try:
54 from setuptools import setup, find_packages
54 from setuptools import setup, find_packages
55 except ImportError:
55 except ImportError:
56 from ez_setup import use_setuptools
56 from ez_setup import use_setuptools
57 use_setuptools()
57 use_setuptools()
58 from setuptools import setup, find_packages
58 from setuptools import setup, find_packages
59 #packages
59 #packages
60 packages = find_packages(exclude=['ez_setup'])
60 packages = find_packages(exclude=['ez_setup'])
61
61
62 setup(
62 setup(
63 name='RhodeCode',
63 name='RhodeCode',
64 version=get_version(),
64 version=get_version(),
65 description=description,
65 description=description,
66 long_description=long_description,
66 long_description=long_description,
67 keywords='rhodiumcode mercurial web hgwebdir gitweb git replacement serving hgweb rhodecode',
67 keywords='rhodiumcode mercurial web hgwebdir gitweb git replacement serving hgweb rhodecode',
68 license='BSD',
68 license='BSD',
69 author='Marcin Kuzminski',
69 author='Marcin Kuzminski',
70 author_email='marcin@python-works.com',
70 author_email='marcin@python-works.com',
71 url='http://hg.python-works.com',
71 url='http://hg.python-works.com',
72 install_requires=requirements,
72 install_requires=requirements,
73 classifiers=classifiers,
73 classifiers=classifiers,
74 setup_requires=["PasteScript>=1.6.3"],
74 setup_requires=["PasteScript>=1.6.3"],
75 data_files=data_files,
75 data_files=data_files,
76 packages=packages,
76 packages=packages,
77 include_package_data=True,
77 include_package_data=True,
78 test_suite='nose.collector',
78 test_suite='nose.collector',
79 package_data=package_data,
79 package_data=package_data,
80 message_extractors={'rhodecode': [
80 message_extractors={'rhodecode': [
81 ('**.py', 'python', None),
81 ('**.py', 'python', None),
82 ('templates/**.mako', 'mako', {'input_encoding': 'utf-8'}),
82 ('templates/**.mako', 'mako', {'input_encoding': 'utf-8'}),
83 ('public/**', 'ignore', None)]},
83 ('public/**', 'ignore', None)]},
84 zip_safe=False,
84 zip_safe=False,
85 paster_plugins=['PasteScript', 'Pylons'],
85 paster_plugins=['PasteScript', 'Pylons'],
86 entry_points="""
86 entry_points="""
87 [paste.app_factory]
87 [paste.app_factory]
88 main = rhodecode.config.middleware:make_app
88 main = rhodecode.config.middleware:make_app
89
89
90 [paste.app_install]
90 [paste.app_install]
91 main = pylons.util:PylonsInstaller
91 main = pylons.util:PylonsInstaller
92
93 [paste.global_paster_command]
94 make-index = rhodecode.lib.indexers:MakeIndex
95 upgrade-db = rhodecode.lib.utils:UpgradeDb
96
92 """,
97 """,
93 )
98 )
General Comments 0
You need to be logged in to leave comments. Login now