--- a/__pkginfo__.py Tue May 18 18:18:08 2010 +0200
+++ b/__pkginfo__.py Thu May 20 20:47:13 2010 +0200
@@ -40,7 +40,7 @@
]
__depends__ = {
- 'logilab-common': '>= 0.50.1',
+ 'logilab-common': '>= 0.50.2',
'logilab-mtconverter': '>= 0.6.0',
'rql': '>= 0.26.0',
'yams': '>= 0.28.1',
--- a/debian/control Tue May 18 18:18:08 2010 +0200
+++ b/debian/control Thu May 20 20:47:13 2010 +0200
@@ -97,7 +97,7 @@
Package: cubicweb-common
Architecture: all
XB-Python-Version: ${python:Versions}
-Depends: ${python:Depends}, graphviz, gettext, python-logilab-mtconverter (>= 0.6.0), python-logilab-common (>= 0.50.1), python-yams (>= 0.29.0), python-rql (>= 0.26.0), python-lxml
+Depends: ${python:Depends}, graphviz, gettext, python-logilab-mtconverter (>= 0.6.0), python-logilab-common (>= 0.50.2), python-yams (>= 0.29.0), python-rql (>= 0.26.0), python-lxml
Recommends: python-simpletal (>= 4.0), python-crypto
Conflicts: cubicweb-core
Replaces: cubicweb-core
--- a/devtools/__init__.py Tue May 18 18:18:08 2010 +0200
+++ b/devtools/__init__.py Thu May 20 20:47:13 2010 +0200
@@ -274,7 +274,6 @@
def init_test_database_sqlite(config):
"""initialize a fresh sqlite databse used for testing purpose"""
# remove database file if it exists
- dbfile = config.sources()['system']['db-name']
if not reset_test_database_sqlite(config):
# initialize the database
import shutil
--- a/etwist/server.py Tue May 18 18:18:08 2010 +0200
+++ b/etwist/server.py Thu May 20 20:47:13 2010 +0200
@@ -41,6 +41,7 @@
from cubicweb.web import dumps
from logilab.common.decorators import monkeypatch
+from logilab.common.daemon import daemonize
from cubicweb import AuthenticationError, ConfigurationError, CW_EVENT_MANAGER
from cubicweb.web import Redirect, DirectResponse, StatusResponse, LogOut
@@ -49,30 +50,6 @@
from cubicweb.etwist.request import CubicWebTwistedRequestAdapter
from cubicweb.etwist.http import HTTPResponse
-def daemonize():
- # XXX unix specific
- # XXX factorize w/ code in cw.server.server and cw.server.serverctl
- # (start-repository command)
- # See http://www.erlenstar.demon.co.uk/unix/faq_toc.html#TOC16
- if os.fork(): # launch child and...
- return 1
- os.setsid()
- if os.fork(): # launch child again.
- return 1
- # move to the root to avoit mount pb
- os.chdir('/')
- # set paranoid umask
- os.umask(077)
- null = os.open('/dev/null', os.O_RDWR)
- for i in range(3):
- try:
- os.dup2(null, i)
- except OSError, e:
- if e.errno != errno.EBADF:
- raise
- os.close(null)
- return None
-
def start_task(interval, func):
lc = task.LoopingCall(func)
# wait until interval has expired to actually start the task, else we have
@@ -423,15 +400,8 @@
raise ConfigurationError("Under windows, you must use the service management "
"commands (e.g : 'net start my_instance)'")
print 'instance starting in the background'
- if daemonize():
+ if daemonize(config['pid-file']):
return # child process
- if config['pid-file']:
- # ensure the directory where the pid-file should be set exists (for
- # instance /var/run/cubicweb may be deleted on computer restart)
- piddir = os.path.dirname(config['pid-file'])
- if not os.path.exists(piddir):
- os.makedirs(piddir)
- file(config['pid-file'], 'w').write(str(os.getpid()))
root_resource.init_publisher() # before changing uid
if config['uid'] is not None:
try:
--- a/etwist/twconfig.py Tue May 18 18:18:08 2010 +0200
+++ b/etwist/twconfig.py Thu May 20 20:47:13 2010 +0200
@@ -39,18 +39,30 @@
options = merge_options((
# ctl configuration
+ ('port',
+ {'type' : 'int',
+ 'default': None,
+ 'help': 'http server port number (default to 8080)',
+ 'group': 'web', 'level': 0,
+ }),
+ ('max-post-length',
+ {'type' : 'bytes',
+ 'default': '100MB',
+ 'help': 'maximum length of HTTP request. Default to 100 MB.',
+ 'group': 'web', 'level': 1,
+ }),
+ ('profile',
+ {'type' : 'string',
+ 'default': None,
+ 'help': 'profile code and use the specified file to store stats if this option is set',
+ 'group': 'web', 'level': 3,
+ }),
('host',
{'type' : 'string',
'default': None,
'help': 'host name if not correctly detectable through gethostname',
'group': 'main', 'level': 1,
}),
- ('port',
- {'type' : 'int',
- 'default': None,
- 'help': 'http server port number (default to 8080)',
- 'group': 'main', 'level': 0,
- }),
('pid-file',
{'type' : 'string',
'default': Method('default_pid_file'),
@@ -64,24 +76,12 @@
the repository rather than the user running the command',
'group': 'main', 'level': WebConfiguration.mode == 'system'
}),
- ('max-post-length',
- {'type' : 'bytes',
- 'default': '100MB',
- 'help': 'maximum length of HTTP request. Default to 100 MB.',
- 'group': 'main', 'level': 1,
- }),
('session-time',
{'type' : 'time',
'default': '30min',
'help': 'session expiration time, default to 30 minutes',
'group': 'main', 'level': 1,
}),
- ('profile',
- {'type' : 'string',
- 'default': None,
- 'help': 'profile code and use the specified file to store stats if this option is set',
- 'group': 'main', 'level': 3,
- }),
('pyro-server',
{'type' : 'yn',
# pyro is only a recommends by default, so don't activate it here
--- a/server/migractions.py Tue May 18 18:18:08 2010 +0200
+++ b/server/migractions.py Thu May 20 20:47:13 2010 +0200
@@ -1200,11 +1200,15 @@
source = self.repo.system_source
storage = source.storage(etype, attribute)
source.unset_storage(etype, attribute)
- rset = self.rqlexec('Any X,A WHERE X is %s, X %s A'
- % (etype, attribute), ask_confirm=False)
+ rset = self.rqlexec('Any X WHERE X is %s' % etype, ask_confirm=False)
pb = ProgressBar(len(rset))
for entity in rset.entities():
+ # fill cache. Do not fetch that attribute using the global rql query
+ # since we may exhaust memory doing that....
+ getattr(entity, attribute)
storage.migrate_entity(entity, attribute)
+ # remove from entity cache to avoid memory exhaustion
+ del entity[attribute]
pb.update()
print
source.set_storage(etype, attribute, storage)
--- a/server/server.py Tue May 18 18:18:08 2010 +0200
+++ b/server/server.py Thu May 20 20:47:13 2010 +0200
@@ -15,9 +15,8 @@
#
# You should have received a copy of the GNU Lesser General Public License along
# with CubicWeb. If not, see <http://www.gnu.org/licenses/>.
-"""Pyro RQL server
+"""Pyro RQL server"""
-"""
__docformat__ = "restructuredtext en"
import os
@@ -26,6 +25,8 @@
import warnings
from time import localtime, mktime
+from logilab.common.daemon import daemonize
+
from cubicweb.cwconfig import CubicWebConfiguration
from cubicweb.server.repository import Repository
@@ -83,7 +84,6 @@
self.quiting = None
# event queue
self.events = []
- # start repository looping tasks
def add_event(self, event):
"""add an event to the loop"""
@@ -103,6 +103,7 @@
def run(self, req_timeout=5.0):
"""enter the service loop"""
+ # start repository looping tasks
self.repo.start_looping_tasks()
while self.quiting is None:
try:
@@ -130,35 +131,7 @@
signal.signal(signal.SIGINT, lambda x, y, s=self: s.quit())
signal.signal(signal.SIGTERM, lambda x, y, s=self: s.quit())
- def daemonize(self, pid_file=None):
- """daemonize the process"""
- # fork so the parent can exist
- if (os.fork()):
- return -1
- # deconnect from tty and create a new session
- os.setsid()
- # fork again so the parent, (the session group leader), can exit.
- # as a non-session group leader, we can never regain a controlling
- # terminal.
- if (os.fork()):
- return -1
- # move to the root to avoit mount pb
- os.chdir('/')
- # set paranoid umask
- os.umask(077)
- if pid_file is not None:
- # write pid in a file
- f = open(pid_file, 'w')
- f.write(str(os.getpid()))
- f.close()
- # filter warnings
- warnings.filterwarnings('ignore')
- # close standard descriptors
- sys.stdin.close()
- sys.stdout.close()
- sys.stderr.close()
-
from logging import getLogger
from cubicweb import set_log_methods
LOGGER = getLogger('cubicweb.reposerver')
-set_log_methods(CubicWebConfiguration, LOGGER)
+set_log_methods(RepositoryServer, LOGGER)
--- a/server/serverctl.py Tue May 18 18:18:08 2010 +0200
+++ b/server/serverctl.py Thu May 20 20:47:13 2010 +0200
@@ -525,6 +525,7 @@
)
def run(self, args):
+ from logilab.common.daemon import daemonize
from cubicweb.server.server import RepositoryServer
appid = pop_arg(args, msg='No instance specified !')
config = ServerConfiguration.config_for(appid)
@@ -544,7 +545,7 @@
piddir = os.path.dirname(pidfile)
if not os.path.exists(piddir):
os.makedirs(piddir)
- if not debug and server.daemonize(pidfile) == -1:
+ if not debug and daemonize(pidfile) == -1:
return
uid = config['uid']
if uid is not None:
--- a/server/sources/native.py Tue May 18 18:18:08 2010 +0200
+++ b/server/sources/native.py Thu May 20 20:47:13 2010 +0200
@@ -33,6 +33,7 @@
from datetime import datetime
from base64 import b64decode, b64encode
from contextlib import contextmanager
+from os.path import abspath
from logilab.common.compat import any
from logilab.common.cache import Cache
@@ -264,6 +265,7 @@
if self.dbdriver == 'sqlite' and \
not getattr(repo.config, 'no_sqlite_wrap', False):
from cubicweb.server.sources.extlite import ConnectionWrapper
+ self.dbhelper.dbname = abspath(self.dbhelper.dbname)
self.get_connection = lambda: ConnectionWrapper(self)
self.check_connection = lambda cnx: cnx
def pool_reset(cnx):
--- a/server/sources/storages.py Tue May 18 18:18:08 2010 +0200
+++ b/server/sources/storages.py Thu May 20 20:47:13 2010 +0200
@@ -82,7 +82,7 @@
XXX subject to race condition.
"""
- path = osp.join(dirpath, basename)
+ path = osp.join(dirpath, basename.replace(osp.sep, '-'))
if not osp.isfile(path):
return path
base, ext = osp.splitext(path)
--- a/web/form.py Tue May 18 18:18:08 2010 +0200
+++ b/web/form.py Thu May 20 20:47:13 2010 +0200
@@ -80,8 +80,6 @@
__metaclass__ = metafieldsform
__registry__ = 'forms'
- internal_fields = ('__errorurl',) + controller.NAV_FORM_PARAMETERS
-
parent_form = None
force_session_key = None
domid = 'form'
--- a/web/views/basecontrollers.py Tue May 18 18:18:08 2010 +0200
+++ b/web/views/basecontrollers.py Thu May 20 20:47:13 2010 +0200
@@ -314,6 +314,9 @@
for name, value in zip(names, values):
# remove possible __action_xxx inputs
if name.startswith('__action'):
+ if action is None:
+ # strip '__action_' to get the actual action name
+ action = name[9:]
continue
# form.setdefault(name, []).append(value)
if name in form:
--- a/web/views/forms.py Tue May 18 18:18:08 2010 +0200
+++ b/web/views/forms.py Thu May 20 20:47:13 2010 +0200
@@ -222,8 +222,6 @@
__regid__ = 'base'
__select__ = (match_kwargs('entity')
| (one_line_rset() & non_final_entity()))
-
- internal_fields = FieldsForm.internal_fields + ('__type', 'eid', '__maineid')
domid = 'entityForm'
@iclassmethod
--- a/web/webconfig.py Tue May 18 18:18:08 2010 +0200
+++ b/web/webconfig.py Thu May 20 20:47:13 2010 +0200
@@ -86,20 +86,20 @@
{'type' : 'string',
'default': None,
'help': 'login of the CubicWeb user account to use for anonymous user (if you want to allow anonymous)',
- 'group': 'main', 'level': 1,
+ 'group': 'web', 'level': 1,
}),
('anonymous-password',
{'type' : 'string',
'default': None,
'help': 'password of the CubicWeb user account to use for anonymous user, '
'if anonymous-user is set',
- 'group': 'main', 'level': 1,
+ 'group': 'web', 'level': 1,
}),
('query-log-file',
{'type' : 'string',
'default': None,
'help': 'web instance query log file',
- 'group': 'main', 'level': 3,
+ 'group': 'web', 'level': 3,
}),
# web configuration
('https-url',