{
"info": {
"author": "BlueDynamics Alliance",
"author_email": "dev@bluedynamics.com",
"bugtrack_url": null,
"classifiers": [
"License :: OSI Approved :: BSD License",
"Operating System :: OS Independent",
"Programming Language :: Python",
"Topic :: Software Development"
],
"description": "relstorage_packer\n=================\n\nPacks a ZODB in a *history-free* PostgreSQL RelStorage with blobs in\nfilesystem.\n\n\nOverview\n--------\n\nThis script works also for very large Relstorage ZODBs with several million\nobjects. The original pack script took several days and consumed lots of RAM.\nSo there was need to accelerate the process of packing.\n\nThis script does not consume relevant amounts of RAM, runs much faster than the\noriginal. Where the old took 3.5 days only for analysis it takes now about 6\nhours. On subsequent runs it only processes changes after last run: it\nconsiders only transactions newer than last processed transaction of the prior\nrun.\n\nAt time of writing processing 44mio objects takes initially about 3-6h\ndepending on hardware and configuration of Postgresql.\n\nThe script creates an inverse object graph, this takes little extra space in DB.\n\n\nLimitations\n-----------\n\nAt time of development the critical production environment was a postgresql\ndatabase running relstorage with blobs stored on a fileserver in history free\nmode. So this is implemented.\n\nI'am sure its easily possible to make this work on MySQL and Oracle too.\nAlso considering blobs inside DB is for sure possible.\n\nI'am not sure if this way of cleanup makes sense for non-history-free mode. At\nleast it needs a lot of love and understanding of ZODB to refactor and\nimplement.\n\nContributions are welcome!\n\n\nUsage\n-----\n\nCreate a configuration file. It is the same as used in classical pack script\ndeployed with Relstorage::\n\n \n create-schema false\n keep-history false\n shared-blob-dir true\n blob-dir var/blobstorage\n commit-lock-timeout 600\n \n dsn dbname='test_site' host='127.0.0.1' user='zodb' password='secret'\n \n \n\nAfter installation a script ``relstorage_pack`` is available::\n\n Usage: relstorage_pack config_file\n\n Fast ZODB Relstorage Packer for history free PostgreSQL\n \n Options:\n -h, --help show this help message and exit\n -i, --init Removes all reference counts and starts from scratch.\n -v, --verbose More verbose output, includes debug messages.\n\nWhen running first time with your database pass ``--init`` as parameter. This\ndrops and recreates the packing table.\n\n\nHow it works\n============\n\nAt first run it creates a table ``object_inrefs`` used for inverse reference\ncounting. The table has:\n\n``zoid BIGINT NOT NULL,``\n this is the object id where incoming references are counted for\n\n``tid BIGINT NOT NULL CHECK (tid > 0)``\n transaction id of the zoid\n\n``inref BIGINT,``\n the object id of the incoming reference OR\n the same as zoid.\n\n``numinrefs BIGINT NOT NULL DEFAULT 0,``\n if zoid==inref this is the counter field, otherwise it is not relevant.\n\nSo this table is used for two different things:\n\n1) keeping track of the incoming references\n\n2) counting the incoming references.\n\nThe code runs in three main phases:\n\ninitial preparation phase\n creates missing tables, cleans object_inrefs table and runs through all\n transactions in order to count and record all transactions.\n\nsubsequent runs preparation phase\n 1) starts at last know tid and then runs through all new\n transactions in order to count and record changes of new transactions.\n 2) for each new transaction zoid (current) check also if there where\n references gone meanwhile. so get all prior filed references of current\n and remove any not valid anymore. For each removed decrement the counter\n on ``object_inrefs`` where zoid=reference and inref=reference.\n\ncleanup phase\n 1) select an orphan, a zoid with no incoming refs\n 2) get all zoids referenced by this orphan\n 3) for each of this reference delete the entry from ``object_inrefs`` where\n inref=orphan and zoid=reference\n 4) decrement counter on the entry where zoid=reference and inref=reference\n 5) delete the entry with the orphaned zoid from ``object_state`` (real data)\n 6) start with (1) unless theres no orphan any more.\n\n\nSource Code\n===========\n\nThe sources are in a GIT DVCS with its main branches at\n`github `_.\n\nWe'd be happy to see many forks and pull-requests to make this package even\nbetter.\n\nUsing integrated buildout and testing\n-------------------------------------\n\nTesting this code i not easy and writing good tests is a task to be done.\nAt the moment you can try the code bu running a\npostgres database on localhost (unless you want to change ``buildout.cfg``).\nThen run as database-user (named ``postgres`` on debian) the commands::\n\n psql -c \"CREATE USER zope WITH PASSWORD 'secret';\"\n psql -c \"CREATE DATABASE relstorage_packer_test OWNER zope;\"\n psql -c \"REVOKE connect ON DATABASE relstorage_packer_test FROM PUBLIC;\"\n psql -c \"GRANT connect ON DATABASE relstorage_packer_test TO zope;\"\n \nNext (because of my laziness) run ``./bin/instance start`` which starts a Plone.\nAdd a Plone Site, add and delete some content to fill the database with\nsomething to pack.\n\nNext run the packer.\n\nIf you dont like this: pull requests are always welcome.\n\nContributors\n============\n\n- Jens W. Klein (Maintainer)\n\nThanks to Robert Penz for some good ideas at our Linux User Group Tirol Meeting.\nAlso thanks to Shane Hathaway for ``Relstorage`` and Jim Fulton for ZODB and\n``zc.zodbdgc`` (which unfortunately does not work with Relstorage).\n\nHistory\n=======\n\n2.1 (2014-02-19)\n----------------\n\n- refactored logging, because it was always in my way when changing other parts \n of the code.\n [jensens, 2014-02-19]\n\n- after long running connections postgresql takes lots of RAM. So we reconnect\n every 5000 cycles (TID analyzing or ZOID removal).\n [jensens, 2014-02-18]\n\n- we had a whole bunch of ``idle in transaction (aborted)`` postgres\n processes running after packing. This resulted in in an ``OperationalError:\n out of shared memory HINT: You might need to increase\n max_pred_locks_per_transaction.`` Error. As a result I refactored the\n transaction handling and rollback and use explicit commit instead of using\n the relstorage ``storage._with_store``. Now this part is very controlled\n and not the source of hanging connections w/o rollback.\n [jensens, 2014-02-18]\n\n\n2.0.2 (2014-02-05)\n------------------\n\n- also support storages w/o blobstorage\n [jensens, 2014-02-05]\n\n\n2.0.1 (2014-02-03)\n------------------\n\n- unlock in a finally to really unlock an failure\n [jensens, 2014-02-03]\n\n- use non-zero exit code if lock could not be aquired.\n [saily]\n\n\n2.0\n---\n\n- refactored the way of collecting and using the reference counts. faster now.\n [jensens, 2014-01-11]\n\n1.0\n---\n\n- started package\n [jensens, 2013-11-23]\n\nLicense\n=======\n\nCopyright (c) 2013, BlueDynamics Alliance, Austria, Germany, Switzerland\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions are met:\n\n* Redistributions of source code must retain the above copyright notice, this \n list of conditions and the following disclaimer.\n* Redistributions in binary form must reproduce the above copyright notice, this \n list of conditions and the following disclaimer in the documentation and/or \n other materials provided with the distribution.\n* Neither the name of the BlueDynamics Alliance nor the names of its \n contributors may be used to endorse or promote products derived from this \n software without specific prior written permission.\n \nTHIS SOFTWARE IS PROVIDED BY BlueDynamics Alliance ``AS IS`` AND ANY\nEXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED\nWARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE\nDISCLAIMED. IN NO EVENT SHALL BlueDynamics Alliance BE LIABLE FOR ANY\nDIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES\n(INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND\nON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT\n(INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS\nSOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.",
"description_content_type": null,
"docs_url": null,
"download_url": "UNKNOWN",
"downloads": {
"last_day": -1,
"last_month": -1,
"last_week": -1
},
"home_page": "http://pypi.python.org/pypi/relstorage_packer",
"keywords": "postgresql zodb pack zope",
"license": "Simplified BSD",
"maintainer": null,
"maintainer_email": null,
"name": "relstorage_packer",
"package_url": "https://pypi.org/project/relstorage_packer/",
"platform": "UNKNOWN",
"project_url": "https://pypi.org/project/relstorage_packer/",
"project_urls": {
"Download": "UNKNOWN",
"Homepage": "http://pypi.python.org/pypi/relstorage_packer"
},
"release_url": "https://pypi.org/project/relstorage_packer/2.1/",
"requires_dist": null,
"requires_python": null,
"summary": "Packs a History Free PostgreSQL RelStorage for ZODB.",
"version": "2.1"
},
"last_serial": 1004784,
"releases": {
"1.0": [
{
"comment_text": "",
"digests": {
"md5": "2412ef57bcfc05cc3951702a0cb50f89",
"sha256": "80d772e85f3ce6031d10b213df96d1b3cfd176869c89289535f34ca1607d45d1"
},
"downloads": -1,
"filename": "relstorage_packer-1.0.tar.gz",
"has_sig": false,
"md5_digest": "2412ef57bcfc05cc3951702a0cb50f89",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 7972,
"upload_time": "2013-11-21T22:50:54",
"url": "https://files.pythonhosted.org/packages/ab/60/201de34086efe453a6e4a42a5709997554485b7e9ca5e94e6c6bb9410aef/relstorage_packer-1.0.tar.gz"
}
],
"2.0.1": [
{
"comment_text": "",
"digests": {
"md5": "f5c913ed3244edbad9185c400caf68a2",
"sha256": "9173bca33b265599dbf2873a16b684afa9aeb1f8a031aed3eadc0287089b59c5"
},
"downloads": -1,
"filename": "relstorage_packer-2.0.1.zip",
"has_sig": false,
"md5_digest": "f5c913ed3244edbad9185c400caf68a2",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 19297,
"upload_time": "2014-02-03T10:40:51",
"url": "https://files.pythonhosted.org/packages/9d/15/f3d78ba0f7c728d37f049ff9a3f6c2d7ca74d0830219622e60700ee9a770/relstorage_packer-2.0.1.zip"
}
],
"2.0.2": [
{
"comment_text": "",
"digests": {
"md5": "0514e54c38a3308e8a90188ce5cd7459",
"sha256": "038a93e30d2cc4df4a8a11d908442bd988102bd2c8bcd2484d89759ced4ac099"
},
"downloads": -1,
"filename": "relstorage_packer-2.0.2.zip",
"has_sig": false,
"md5_digest": "0514e54c38a3308e8a90188ce5cd7459",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 19420,
"upload_time": "2014-02-05T14:43:10",
"url": "https://files.pythonhosted.org/packages/2b/9b/52b984825275e4921efad1d9e4eccfc7be1f06d516dd1d884e9eba57e129/relstorage_packer-2.0.2.zip"
}
],
"2.1": [
{
"comment_text": "",
"digests": {
"md5": "4ab7ae96ea3d652bf0c2560da50ff22c",
"sha256": "16122098263731996d1db1fe45f9c30db42e9775949c44f52614f450942886a1"
},
"downloads": -1,
"filename": "relstorage_packer-2.1.tar.gz",
"has_sig": false,
"md5_digest": "4ab7ae96ea3d652bf0c2560da50ff22c",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 11154,
"upload_time": "2014-02-19T12:07:05",
"url": "https://files.pythonhosted.org/packages/ac/f2/27233ae523db5a1af754640821ee5c2161ba0d563978a507f1302be84299/relstorage_packer-2.1.tar.gz"
}
]
},
"urls": [
{
"comment_text": "",
"digests": {
"md5": "4ab7ae96ea3d652bf0c2560da50ff22c",
"sha256": "16122098263731996d1db1fe45f9c30db42e9775949c44f52614f450942886a1"
},
"downloads": -1,
"filename": "relstorage_packer-2.1.tar.gz",
"has_sig": false,
"md5_digest": "4ab7ae96ea3d652bf0c2560da50ff22c",
"packagetype": "sdist",
"python_version": "source",
"requires_python": null,
"size": 11154,
"upload_time": "2014-02-19T12:07:05",
"url": "https://files.pythonhosted.org/packages/ac/f2/27233ae523db5a1af754640821ee5c2161ba0d563978a507f1302be84299/relstorage_packer-2.1.tar.gz"
}
]
}