{ "info": { "author": "Arjan Verkerk", "author_email": "arjan.verkerk@nelen-schuurmans.nl", "bugtrack_url": null, "classifiers": [], "description": "Turn\n====\n\n\nIntroduction\n------------\nTurn is a shared-resource-locking queue system using python and Redis. Use\nit in separate programs that acess the same shared resource to make\nsure each program waits for its turn to handle the resource.\n\nIt is inspired on a the queueing system that is sometimes found in small\nshops, consisting of a serial number dispenser and a wall indicator.\n\nTurn comes with a commandline tool for resetting and direct inspection\nof queues, and listening to message channels for one or more resources.\n\n\nInstallation\n------------\n\nInstall turn with pip::\n\n $ pip install turn\n\nOf course, you should also have a Redis server at hand.\n\n\nUsage\n-----\n\nBasic usage goes like this::\n\n import turn\n\n # a locker corresponds to a reusable Redis client\n locker = turn.Locker(host='localhost', port=6379, db=0)\n\n resource = 'my_valuable_resource'\n label = 'This shows up in messages.'\n\n with locker.lock(resource=resource, label=label):\n pass # do your careful work on the resource here\n\nlock() accepts two extra keyword arguments:\n\nexpire: maximum expire value for a users presence (default 60)\n\nIf a user crashes hard, its presence in the queue will be kept\nalive at most ``expire`` seconds. This value affects how often the EXPIRE\ncommand will be sent to Redis to signal the continuing presence of a\nuser in the queue.\n\npatience: period of waiting before bumping the queue (default 60)\n\nIf a program waits longer than this value without receiving any\nprogression messages on the queues pubsub channel, it will bump the\nqueue to see if any users have left the queue in an unusual way.\n\n\nTools\n-----\nThe state of users and queues can be monitered by inspection of Redis\nvalues and subscription to Redis channels.\n\nInspection can be done using the console script requesting a snap-shot\nstatus report::\n\n $ turn status my_valuable_resource --host localhost\n my_valuable_resource 5\n ------------------------------------------------------------\n This shows up in status reports and messages. 5\n\nRunning ``turn status`` without specifying any resources, produces a summary\nof all queues within the database.\n\nAlternatively, one or more subscriptions to the Redis PubSub channels\nfor a particular resource can be followed::\n\n $ turn follow my_valuable_resource --port 6379\n my_valuable_resource: 5 assigned to \"This shows up in messages.\"\n my_valuable_resource: 5 started\n my_valuable_resource: 5 completed by \"This shows up in messages.\"\n my_valuable_resource: 6 granted\n\nSimilar to the status command, running ``turn follow`` without specifying\nany resources starts following the channels for any queue currently\nwithin the database. Note that new queues are not automatically added\nto the subscription.\n\nQueues can also be reset (removed) from Redis using ``turn reset``\noptionally followed by resources queues to reset. Reset without\nresource names resets all available queues in the server. If a queue\nfor a resource shows activity, it will not be reset and in addition a\nmessage will be produced. A reset command for a resource will also 'bump'\nthe queue for that resource.\n\n\nImplementation details\n----------------------\nWhen a lock is requested, a unique serial number is obtained from Redis\nvia INCR on a Redis value, called the dispenser. The lock is acquired\nonly if another value, called the indicator, corresponds to the unique\nserial number.\n\nThere are two mechanisms that can change the indicator:\n\n1. The user with the corresponding serial number is finished acting on the\n shared resource and increases the number, notifying any other subscribed\n waiting users. This is the preferred way to handle things.\n\n2. Another user gets impatient and calls the bump procedure. This\n procedure checks if the user corresponding to the indicator is\n still active and if necessary sets the indicator to an appropriate\n value.\n \nActivity is monitored via an expiring key-value pair in Redis. The turn\nlibrary automatically arranges a thread that keeps updating the expiration\ntime, to make sure the presence does not expire during waiting for,\nor handling of the resource.\n\n\nCredits\n=======\n\n- Written by Arjan Verkerk\n\n\nChanges\n=======\n\n\n0.5 (2015-12-28)\n----------------\n\n- Python 3 compatible.\n\n- Add lock tool for locking multiple resources from console.\n\n\n0.4 (2015-04-30)\n----------------\n\n- Add more help to the console script.\n\n- Add serious tests regarding safety.\n\n\n0.3.1 (2015-04-30)\n------------------\n\n- Reshuffled of tests and docs.\n\n\n0.3 (2015-04-30)\n----------------\n\n- All code covered by tests.\n\n- Extend docs.\n\n\n0.2.1 (2015-04-28)\n------------------\n\n- Patience adjusted to seconds.\n\n- PubSub connections closed automatically.\n\n- Make patience an argument of lock().\n\n- Docs updated.\n\n\n0.2 (2015-04-28)\n----------------\n\n- Documentation adjustments.\n\n- Move console stuff to separate module.\n\n- Use select and not poll, to make increase platform independency.\n\n- Use the name 'Locker' for the reusable object that locks things.\n\n\n0.1.1 (2015-04-23)\n------------------\n\n- You can use pip now.\n\n\n0.1 (2015-04-23)\n----------------\n\n- Initial project structure created with nensskel 1.36.dev0.\n\n- First working version.", "description_content_type": null, "docs_url": null, "download_url": "", "downloads": { "last_day": -1, "last_month": -1, "last_week": -1 }, "home_page": "https://github.com/nens/turn", "keywords": "redis,queue,resource,shared", "license": "GPL", "maintainer": "", "maintainer_email": "", "name": "turn", "package_url": "https://pypi.org/project/turn/", "platform": "UNKNOWN", "project_url": "https://pypi.org/project/turn/", "project_urls": { "Homepage": "https://github.com/nens/turn" }, "release_url": "https://pypi.org/project/turn/0.5/", "requires_dist": null, "requires_python": "", "summary": "A shared-resource-locking queue system using python and redis.", "version": "0.5" }, "last_serial": 1880084, "releases": { "0.1": [ { "comment_text": "", "digests": { "md5": "8426df32d58c03451abc7366b731dee6", "sha256": "2ef03ec465f53c3f62dbdb54e76499568d0bcaea592f3935ded3b1ebdb3fa13b" }, "downloads": -1, "filename": "turn-0.1.tar.gz", "has_sig": false, "md5_digest": "8426df32d58c03451abc7366b731dee6", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 18897, "upload_time": "2015-04-23T13:57:35", "url": "https://files.pythonhosted.org/packages/95/4b/083f669432ca674ff1e19a87f43bf6a662e321d21def548963dbb971cbcf/turn-0.1.tar.gz" } ], "0.1.1": [ { "comment_text": "", "digests": { "md5": "ba2f71c85afbe06bbb92eae05b57ceba", "sha256": "89dadf3102d70a01eedb8580f2b821f9e21108a140fecac42e2c8002219cf7b6" }, "downloads": -1, "filename": "turn-0.1.1.tar.gz", "has_sig": false, "md5_digest": "ba2f71c85afbe06bbb92eae05b57ceba", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 18907, "upload_time": "2015-04-23T14:05:42", "url": "https://files.pythonhosted.org/packages/36/0f/8f3ffb9e48a730a1b7145e1a40873f8b4dc8024c80af8ea61f3289f99a20/turn-0.1.1.tar.gz" } ], "0.2": [ { "comment_text": "", "digests": { "md5": "6e47f040d7557df84c60940ceb3e156b", "sha256": "8a76f7ac4f3951869df9d7a209e87ff8662cc3d1f5d178109d1ba6620904c287" }, "downloads": -1, "filename": "turn-0.2.tar.gz", "has_sig": false, "md5_digest": "6e47f040d7557df84c60940ceb3e156b", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 19919, "upload_time": "2015-04-28T10:34:38", "url": "https://files.pythonhosted.org/packages/86/5a/a27d8b15868fafb6019cd99f4dd874e6236f05cbd5f420e0edef76c9b875/turn-0.2.tar.gz" } ], "0.2.1": [ { "comment_text": "", "digests": { "md5": "348b668e933b2619db744afcb747f5f6", "sha256": "e309d29f0e054569ef795c868c4cda9feb19f56a0303b55922567ab9ab95a7f9" }, "downloads": -1, "filename": "turn-0.2.1.tar.gz", "has_sig": false, "md5_digest": "348b668e933b2619db744afcb747f5f6", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 20298, "upload_time": "2015-04-28T12:58:37", "url": "https://files.pythonhosted.org/packages/8b/28/82087876ebdd5a2af7caedf607e814bbb7ad7682b28f12da1a4acad2bfd1/turn-0.2.1.tar.gz" } ], "0.3": [ { "comment_text": "", "digests": { "md5": "372b294a6d7d5a91fd3822063c43ca57", "sha256": "a4936b8ea913a51129040b543294b33c580250746506d00fecc42d01d0f11882" }, "downloads": -1, "filename": "turn-0.3.tar.gz", "has_sig": false, "md5_digest": "372b294a6d7d5a91fd3822063c43ca57", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 24797, "upload_time": "2015-04-30T14:05:54", "url": "https://files.pythonhosted.org/packages/ab/d7/7bc0b4e3c96803bff3088ed5da493ee196f70db993e0e75e7ed960030d10/turn-0.3.tar.gz" } ], "0.3.1": [ { "comment_text": "", "digests": { "md5": "8d70ac7b39e70f92343baeaf52b860a4", "sha256": "1f7b76e036ffbc20badc0b6d8e124ac223de825a6aad0cf951feca99cc1f6446" }, "downloads": -1, "filename": "turn-0.3.1.tar.gz", "has_sig": false, "md5_digest": "8d70ac7b39e70f92343baeaf52b860a4", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 24364, "upload_time": "2015-04-30T14:38:07", "url": "https://files.pythonhosted.org/packages/45/5b/10f85e7384c661cb2b8406396cca2093499f85e074dc3dffc0ba9e6cde28/turn-0.3.1.tar.gz" } ], "0.4": [ { "comment_text": "", "digests": { "md5": "504615754c049f80b3dfa5080de95b97", "sha256": "25f5dc2f6021fcfdffe1f61ec93a4199f8a3c1415567087f77e3ebebb8ad4f10" }, "downloads": -1, "filename": "turn-0.4.tar.gz", "has_sig": false, "md5_digest": "504615754c049f80b3dfa5080de95b97", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 21582, "upload_time": "2015-04-30T21:14:08", "url": "https://files.pythonhosted.org/packages/f8/9f/3286703654246b008d4d9d207879859d7f8c5b1700fdbdf3feaff84a037d/turn-0.4.tar.gz" } ], "0.5": [ { "comment_text": "", "digests": { "md5": "1766a57f02db75b679d1e023bf9e00d2", "sha256": "9dde97073fca550c8259c3affb0debf85106ad1c10ae6fe381c03900a8b57895" }, "downloads": -1, "filename": "turn-0.5.tar.gz", "has_sig": false, "md5_digest": "1766a57f02db75b679d1e023bf9e00d2", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 25075, "upload_time": "2015-12-28T15:44:31", "url": "https://files.pythonhosted.org/packages/93/75/8cf0fa0908bf7673d49705bd1f6db17fc806ecd1279ae35a378b66f56b57/turn-0.5.tar.gz" } ] }, "urls": [ { "comment_text": "", "digests": { "md5": "1766a57f02db75b679d1e023bf9e00d2", "sha256": "9dde97073fca550c8259c3affb0debf85106ad1c10ae6fe381c03900a8b57895" }, "downloads": -1, "filename": "turn-0.5.tar.gz", "has_sig": false, "md5_digest": "1766a57f02db75b679d1e023bf9e00d2", "packagetype": "sdist", "python_version": "source", "requires_python": null, "size": 25075, "upload_time": "2015-12-28T15:44:31", "url": "https://files.pythonhosted.org/packages/93/75/8cf0fa0908bf7673d49705bd1f6db17fc806ecd1279ae35a378b66f56b57/turn-0.5.tar.gz" } ] }