{ "info": { "author": "Meeshkan Dev Team", "author_email": "dev@meeshkan.com", "bugtrack_url": null, "classifiers": [ "Development Status :: 2 - Pre-Alpha", "License :: OSI Approved :: Apache Software License", "Operating System :: MacOS", "Operating System :: POSIX", "Operating System :: Unix", "Programming Language :: Python", "Programming Language :: Python :: 3", "Programming Language :: Python :: 3.6", "Programming Language :: Python :: 3.7" ], "description": "\n# Meeshkan client\nThis repository contains Meeshkan client-side code.\n\nFor detailed API reference and usage instructions, please see [meeshkan-client.readthedocs.io](https://meeshkan-client.readthedocs.io).\n\n## Table of contents\n1. [Overview](#overview)\n1. [Quick start](#quick-start)\n1. [Command-line interface](#command-line-interface)\n1. [Remote Control with Slack](#remote-control-with-Slack)\n1. [Usage as Python library](#usage-as-python-library)\n1. [Working with Amazon SageMaker](#working-with-amazon-sagemaker)\n1. [Known issues](#known-issues)\n1. [Development](#development)\n\n## Overview\nClient code consists of two parts: the Meeshkan agent controlled with\n[command-line interface](#command-line-interface) and the [Python library](#usage-as-python-library) `meeshkan`.\n\nUsing the client requires signing up at [meeshkan.com](https://meeshkan.com). If you want to control your jobs\nvia [Slack](https://slack.com/), you also need to set up the Slack integration as explained in the\n[documentation](https://www.meeshkan.com/docs/slack).\n\n### How it works\n#### The Meeshkan agent\nThe agent is a daemonized process running in the background. Agent is responsible\nfor scheduling _jobs_ (Python scripts) and interacting with them. Agent is responsible for, e.g.,\n1. sending job notifications so that you know how your jobs are doing and\n2. listening to instructions from the server. If you remotely execute the command to, for example, stop a job, the agent\ngets the instruction to stop the job from the server and stops the job.\n\nThe agent is managed using the\n[command-line interface (CLI)](#command-line-interface).\n\n#### The Meeshkan Python library\nThe Python library imported with `import meeshkan` is used in scripts to\ncontrol the notifications you get. For example, by including a command such as \n```python\nimport meeshkan\nmeeshkan.report_scalar(\"Train loss\", loss)\n```\nin your Python script you specify that notifications you get should contain the value for `loss`.\nSimilarly, `meeshkan.add_condition` can be used to send notifications for arbitrary events.\nFor detailed documentation of the library usage, see [below](#usage-as-python-library).\n\nNote that using `meeshkan` in your Python scripts is optional (though recommended). If you do\nnot specify reported scalars, you will only get notifications for when jobs start or finish.\n\n## Quick start\n\nPlease see the instructions in [readthedocs.io](https://meeshkan-client.readthedocs.io/en/latest/#quick-start).\n\n## Command-line interface\nTo list available commands, execute `meeshkan` or `meeshkan help`:\n```bash\nUsage: meeshkan [OPTIONS] COMMAND [ARGS]...\n\nOptions:\n -h, --help Show this message and exit.\n --version Show the version and exit.\n\nCommands:\n clean Alias for `meeshkan clear`\n clear Clears Meeshkan log and job directories in ~/.meeshkan.\n help Show this message and exit.\n list Lists the job queue and status for each job.\n logs Retrieves the logs for a given job.\n notifications Retrieves notification history for a given job.\n report Returns latest scalar from given job identifier\n setup Configures the Meeshkan client.\n sorry Send error logs to Meeshkan HQ.\n start Starts Meeshkan service daemon.\n status Checks and returns the service daemon status.\n stop Stops the service daemon.\n submit Submits a new job to the service daemon.\n\n```\n\nIn all instances used, a *JOB_IDENTIFIER* can be either the job's UUID, the job number, or a pattern to match against \nthe job's name. In the latter case, the first match is returned.\n\n### Start the agent\nRunning\n```bash\nmeeshkan start\n```\nstarts the agent as daemonized service.\nIf you get `Unauthorized` error, please check your credentials. Also check [known issues](#known-issues). If the problem persists, please contact Meeshkan support.\n\n### Submit a script for execution\nSubmit a Python script as job:\n```bash\nmeeshkan submit [--name job_name] [--report-interval 60] examples/hello_world.py\n```\nThe agent runs submitted jobs sequentially in first-in-first-out order. By default, the `submit` command will run your code\nwithout time-based notifications (see [below](#reporting-scalars)). When presented with the\n`-r/--report-interval` flag, the service will notify you with recent updates every time\nthe *report interval* has elapsed. The report interval is measured in **seconds**.\nThe default argument (if none are provided) is 3600 seconds (i.e. hourly notifications).\n\n### List submitted jobs\n```bash\nmeeshkan list\n```\n\n### Retrieve stdout and stderr for a job\n```bash\nmeeshkan logs JOB_IDENTIFIER\n```\nHere *JOB_IDENTIFIER* can be either the job's UUID, the job number, or a pattern to match against\nthe job's name.\n\nYou will get a complete output of stderr and stdout for the given job, and it's output path for any additional files.\n\n### Review job notification history\n```bash\nmeeshkan notifications JOB_IDENTIFIER\n```\n\n### Review latest scalar reports\n```bash\nmeeshkan report JOB_IDENTIFER\n```\n\n### Canceling a job\n```bash\nmeeshkan cancel JOB_IDENTIFIER\n```\nIf the job is currently running, you will be prompted to verify you want to abruptly cancel a running job.\n\n### Stop service\n```bash\nmeeshkan stop\n```\n\n## Remote Control with Slack\n\n### Background\nA core functionality of the Meeshkan agent is it's seamless integration with common platforms.\nFor our first integration, we chose to focus on *Slack*.\n\n### Setup and Security \nWhen signing up to the first, you may [integrate your agent](https://www.meeshkan.com/docs/slack) to a specific\nworkspace and channel (the channel may also be a specific user!). From that moment on, you are considered the de-facto\n*admin* for that integration, and by default, you are the **only** user with remote access to the agent.\nWe take security very seriously, and would never expose your machine, code or data to any 3rd party API.\n\nEvery Slack channel may have several integrations. When issuing a remote controlled command (as opposed to responding to\none), the command is assigned to the agent you integrated. If no such agent exists, it is assigned to the agent for\nwhich you are authorized to run remote commands. If more than one such agent exists - well, that shouldn't happen.\n\n### Slash Commands\n\nRemote controlling from Slack means using /slash commands. All Meeshkan-related commands are prefixed with `/mk-*`.\nAs we continue development, we will roll out more and more interactive commands. Eventually, we intend on making things\neven easier with simple NLP mechanisms.\n\n#### Controlling Authorized User List\nTo grant users other than yourself remote access to your agent, you can use the `/mk-auth` command where you integrated\nthe agent. The `/mk-auth` command has 3 subcommands:\n1. `/mk-auth list` (also `/mk-auth ls`): lists the users allowed to run commands remotely.\n1. `/mk-auth add @user1 [@user2 ...]` (also `/mk-auth allow` and `/mk-auth permit`): adds user(s) to the authorized list\n1. `/mk-auth rm @user1 [@user2 ...]` (also `/mk-auth del`, `/mk-auth delete`, `/mk-auth remove`): removes matching users\nfrom the list.\n\n\n#### Running code from GitHub \nYou may issue a remote command to run code from GitHub (if you are authorized to do so) using:\n`/mk-gitrun repo[@commit/branch] entrypoint [job name] [report interval]`.\nWhere you may choose a specific commit/branch to use, but you have to specify a repository and entry point (the file to\nrun). Job name can be extended to multiple words using qutoation marks.\nExamples include:\n```\n/mk-gitrun Meeshkan/meeshkan-client examples/hello_world.py\n/mk-gitrun Meeshkan/meeshkan-client@release-v-0.1.4 examples/hello_world.py \"some long job name\"\n/mk-gitrun Meeshkan/meeshkan-client examples/hello_world.py 10\n```\nTo run code from private repositories, you would need to input a GitHub Access Token with running `meeshkan setup`\n(see the documentation for more information).\n\n#### Stopping a command\nFinally, sometimes you may want to issue a remote command to stop a scheduled or running job.\nThis is done with a simple `/mk-stop job_identifier`, where `job_identifier` corresponds to the same usage as the CLI\n(it may be a job name, number, UUID, pattern, etc...)\n\n## Usage as Python library\n\nFor detailed API reference, see [meeshkan-client.readthedocs.io](https://meeshkan-client.readthedocs.io).\n\n### General\nThe purpose of the Python API is to be as intuitive, minimal and least invasive as possible.\nOnce the agent has been started using `meeshkan start`, you can communicate with it from your\nPython scripts through `meeshkan` library.\n\nTo begin, `import meeshkan`.\n\n### Starting, stopping and restarting the agent\nAs alternatives for the CLI interface, you may use `meeshkan.init(token=...)` to start the agent with a new token. \nIf the agent is already set up via the CLI (`meeshkan setup`), you may simply call `meeshkan.init()` or \n`meeshkan.start()`. \nYou may further restart the agent with `meeshkan.restart()` and stop the agent completely with `meeshkan.stop()`\n\n### Reporting scalars\nYou can report scalars from within a given script using `meeshkan.report_scalar(name1, value1, name2, value2, ...)`.\nThe command allows reporting multiple values at once, and giving them self-documenting names (you may use anything, as\nlong as it's a string!).\n\nSome examples include (assume the mentioned variables exist, and are updated in some loop, e.g. a training/evaluation\nloop):\n```python\nmeeshkan.report_scalar(\"train loss\", train_loss) # Adds a single value for this process\n# Or add multiple scalars simulatenously\nmeeshkan.report_scalar(\"train loss\", train_loss, \"evaluation loss\", eval_loss, \"evaluation accuracy\", eval_acc)\n# Or possibly combine them for a new metric\nmeeshkan.report_scalar(\"F1\", 2*precision*recall/(precision+recall))\n```\n\n### Adding conditions\nThe agent only notifies you on either a scheduled notification (using the `--report-interval/-r` flag, e.g.\nhourly notifications), or when a certain criteria has been met.\nYou can define these criteria anywhere in your code (but outside of loops, these conditions only need to be set once!),\neven before your scalars have been registered. When a scalar is used before it is registered, a default value of 1 is\nused in its place.\n\nConsider the following examples:\n```python\n# Notify when evaluation loss and train loss are significantly different.\nmeeshkan.add_condition(\"train loss\", \"evaluation loss\", lambda train_loss, eval_loss: abs(train_loss - eval_loss) > 0.2)\n# Notify when the F1 score is suspiciously low\nmeeshkan.add_condition(\"F1\", lambda f1: f1 < 0.1)\n```\n\n### Submitting notebooks and/or functions\nWhen working with Jupyter notebooks, one may want to test the entire notebook as a long running task, or test individual\nlong running functions. With Meeshkan, you can easily achieve both of these! \nFrom a notebook instance, you may submit the entire notebook with:\n```python\nmeeshkan.submit_notebook() # Default job name, report interval, for a password-free notebook\n# If your notebook server is password protected, you may need to supply the password:\nmeeshkan.submit_notebook(notebook_password=...)\n# Finally, you can customize the job's name and report interval as well! The full argument list is:\nmeeshkan.submit_notebook(job_name=..., report_interval=..., notebook_password=...)\n```\n\nSometimes, we only need to test out an individual function, or perhaps you would like to skip the time it took to \ndownload, parse and process a dataset. Meeshkan also offers a solution for that via `meeshkan.submit_function`.\nConsider:\n```python\ndef train(optional_args=DEFAULT_VALUES):\n # some training process with global dataset, model, optimizer, etc...\n ...\n\n\nmeeshkan.submit_function(train)\nmeeshkan.submit_function(train, args=[50]) # Sends 50 to optional_args\nmeeshkan.submit_function(train, args=[[50]]) # Sends [50] to optional_args\nmeeshkan.submit_function(train, kwargs={'optional_args': [50]}) # Sends [50] to optional_args via kwargs\n```\n\n## Working with Amazon SageMaker\nFor an example of how to use Meeshkan to monitor [Amazon SageMaker](https://aws.amazon.com/sagemaker/) jobs,\nsee the example [notebook](./examples/sagemaker/pytorch_rnn_meeshkan.ipynb).\n\n## Known issues\n#### Start occasionally fails in macOS\nIn macOS, running `meeshkan start` may fail with\n```\nobjc[60320]: +[NSValue initialize] may have been in progress in another thread when fork() was called. We cannot safely call it or ignore it in the fork() child process. Crashing instead. Set a breakpoint on objc_initializeAfterForkError to debug.\n```\nThis happens because of threading restrictions introduced in macOS High Sierra.\nYou can read more about it [here](https://bugs.python.org/issue30837), [here](https://blog.phusion.nl/2017/10/13/why-ruby-app-servers-break-on-macos-high-sierra-and-what-can-be-done-about-it/), [here](https://github.com/rtomayko/shotgun/issues/69), and [here](https://stackoverflow.com/questions/50168647/multiprocessing-causes-python-to-crash-and-gives-an-error-may-have-been-in-progr).\nWe hope to find a permanent fix for this, but in the meanwhile you can run\n```bash\n$ export OBJC_DISABLE_INITIALIZE_FORK_SAFETY=YES\n```\nbefore starting the client and then try again. If this does not fix the issue, please contact [dev@meeshkan.com](mailto:dev@meeshkan.com).\n\n\n## Development\nWe welcome contributions!\n\n### Install from the source\nFirst clone this repository. Then install dependencies excluding test dependencies:\n```bash\npip install -e .\n```\n\nInclude test dependencies:\n```bash\npip install -e .[dev]\n```\n\n### Running tests\n```bash\npytest [-s]\n```\n\n### Running lint\n```bash\npylint -f msvs meeshkan\n```\nTo check for required coverage:\n```bash\npython run_pylint.py --fail-under=9.75 -f msvs meeshkan\n```\n\n### Running static type checks\n```bash\nmypy meeshkan\n```\nThe configuration for `mypy` can be found in [mypy.ini](./mypy.ini).\n\n### Building the documentation\n```bash\npython setup.py doc\n# OR (the long way...)\ncd docs\nsphinx-apidoc -f -e -o source/ ../meeshkan/\nsphinx-build -M html -D version={VERSION} source build\n```\n\n\n", "description_content_type": "text/markdown", "docs_url": null, "download_url": "", "downloads": { "last_day": -1, "last_month": -1, "last_week": -1 }, "home_page": "https://www.meeshkan.com/", "keywords": "", "license": "Apache 2.0", "maintainer": "", "maintainer_email": "", "name": "meeshkan", "package_url": "https://pypi.org/project/meeshkan/", "platform": "", "project_url": "https://pypi.org/project/meeshkan/", "project_urls": { "Homepage": "https://www.meeshkan.com/" }, "release_url": "https://pypi.org/project/meeshkan/0.1.9/", "requires_dist": [ "boto3", "dill", "jsonschema (<3)", "requests (<2.21)", "Click", "pandas", "Pyro4", "PyYAML", "tabulate", "matplotlib", "nbconvert", "ipykernel", "notebook", "sentry-sdk", "jupyter ; extra == 'dev'", "nbdime ; extra == 'dev'", "pylint ; extra == 'dev'", "pytest (==4.0.2) ; extra == 'dev'", "pytest-cov ; extra == 'dev'", "mypy ; extra == 'dev'", "pytest-asyncio ; extra == 'dev'", "sagemaker ; extra == 'dev'", "sphinx ; extra == 'dev'", "sphinx-click ; extra == 'dev'", "sphinx-rtd-theme ; extra == 'dev'", "jupyter ; extra == 'devtf'", "nbdime ; extra == 'devtf'", "pylint ; extra == 'devtf'", "pytest (==4.0.2) ; extra == 'devtf'", "pytest-cov ; extra == 'devtf'", "mypy ; extra == 'devtf'", "pytest-asyncio ; extra == 'devtf'", "sagemaker ; extra == 'devtf'", "sphinx ; extra == 'devtf'", "sphinx-click ; extra == 'devtf'", "sphinx-rtd-theme ; extra == 'devtf'", "tensorflow ; extra == 'devtf'", "tensorboard ; extra == 'devtf'", "keras ; extra == 'devtf'", "jupyter ; extra == 'devtorch'", "nbdime ; extra == 'devtorch'", "pylint ; extra == 'devtorch'", "pytest (==4.0.2) ; extra == 'devtorch'", "pytest-cov ; extra == 'devtorch'", "mypy ; extra == 'devtorch'", "pytest-asyncio ; extra == 'devtorch'", "sagemaker ; extra == 'devtorch'", "sphinx ; extra == 'devtorch'", "sphinx-click ; extra == 'devtorch'", "sphinx-rtd-theme ; extra == 'devtorch'", "torch ; extra == 'devtorch'" ], "requires_python": ">=3.6.0", "summary": "The Meeshkan Client for interactive machine learning", "version": "0.1.9" }, "last_serial": 4915313, "releases": { "0.0.1": [ { "comment_text": "", "digests": { "md5": "0eeddb9ee0f37d81d726115be84374e9", "sha256": "cba92e68cec89d444fca7737208f7bd9881109175b99b57698a76632f7f29442" }, "downloads": -1, "filename": "meeshkan-0.0.1-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "0eeddb9ee0f37d81d726115be84374e9", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.5.0", "size": 20191, "upload_time": "2018-11-08T15:48:00", "url": "https://files.pythonhosted.org/packages/82/3e/67af2908a3e89dba8bffa2732990b6b625770fc766c84e6d5a40f5ff4f43/meeshkan-0.0.1-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "150215629498e7741864caafada00843", "sha256": "94a5a65013cf01c08c374700d06124d841005c7f3f2c52035e2b5eda528e6dc6" }, "downloads": -1, "filename": "meeshkan-0.0.1.tar.gz", "has_sig": false, "md5_digest": "150215629498e7741864caafada00843", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.5.0", "size": 15975, "upload_time": "2018-11-08T15:48:03", "url": "https://files.pythonhosted.org/packages/f5/2b/3da8b80a8a99137f38d313c58c61d3e2723347c7de87cec2598dfb4e352c/meeshkan-0.0.1.tar.gz" } ], "0.0.11": [ { "comment_text": "", "digests": { "md5": "abb45fe63c1dda8b338820226af025c3", "sha256": "37a23cef3a8719514876658c49d34db96a6a84369a249f5ae3f792b982916aa9" }, "downloads": -1, "filename": "meeshkan-0.0.11-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "abb45fe63c1dda8b338820226af025c3", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.5.0", "size": 24879, "upload_time": "2018-11-19T14:02:33", "url": "https://files.pythonhosted.org/packages/db/da/3c3698f42e10dc13dd03ebbe332feabc3514e192f89347a4ede71d5c2aaa/meeshkan-0.0.11-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "6fe3be7a998f1b254fd228ae2451de01", "sha256": "56365bb833ec65f3b31724de716a69fddbbea0ead8e91c712a20e2bc2848c807" }, "downloads": -1, "filename": "meeshkan-0.0.11.tar.gz", "has_sig": false, "md5_digest": "6fe3be7a998f1b254fd228ae2451de01", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.5.0", "size": 20080, "upload_time": "2018-11-19T14:02:34", "url": "https://files.pythonhosted.org/packages/65/c4/62ef6578feb54a8027aa1cf8a7eed43f3f4957049bce2cac7e24c261fad5/meeshkan-0.0.11.tar.gz" } ], "0.1.0": [ { "comment_text": "", "digests": { "md5": "824e1d5bd1f7ae2ccbdb248988f03334", "sha256": "c2e17b1363f01b12946bdc1afbcd1017ec3250d405a0b53e36b84521cc6dfaa0" }, "downloads": -1, "filename": "meeshkan-0.1.0-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "824e1d5bd1f7ae2ccbdb248988f03334", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.5.0", "size": 28984, "upload_time": "2018-11-26T14:29:14", "url": "https://files.pythonhosted.org/packages/de/0d/f30df38d8bcd60f2854312b9adc2f6e2d5de8f5aa0638c033474e5af8068/meeshkan-0.1.0-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "bc6bd4d2bbb0885f47ca114d39bdc7d1", "sha256": "112178a62b393ce435124f592ab823ad33e7309aacb608f15e5837af684becac" }, "downloads": -1, "filename": "meeshkan-0.1.0.tar.gz", "has_sig": false, "md5_digest": "bc6bd4d2bbb0885f47ca114d39bdc7d1", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.5.0", "size": 23305, "upload_time": "2018-11-26T14:29:16", "url": "https://files.pythonhosted.org/packages/04/6c/790b331d69f0210a565ff11576be41476ef407c25f03d44929ee46ced27b/meeshkan-0.1.0.tar.gz" } ], "0.1.1": [ { "comment_text": "", "digests": { "md5": "e688850cd021676f5989099711509b69", "sha256": "a85b23eb244e8abc8665fc6ad4c0bc63713807845279117817b893185de514a5" }, "downloads": -1, "filename": "meeshkan-0.1.1-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "e688850cd021676f5989099711509b69", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.5.0", "size": 38293, "upload_time": "2018-12-03T15:36:44", "url": "https://files.pythonhosted.org/packages/4b/c1/bf0ed2abf757cdd1f4d66478027caf861212c9c184faadcc2403daca7ab0/meeshkan-0.1.1-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "26107822f042b84077fc843d10647c84", "sha256": "9247518d37f6fed55ecfc7f2832bf31574042974bc913efc4d05ea076bde9e4f" }, "downloads": -1, "filename": "meeshkan-0.1.1.tar.gz", "has_sig": false, "md5_digest": "26107822f042b84077fc843d10647c84", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.5.0", "size": 33038, "upload_time": "2018-12-03T15:36:46", "url": "https://files.pythonhosted.org/packages/0a/cb/2f6f8253ab37f11520bccd58389d0d0c104f589b4b8cc33371cae7534911/meeshkan-0.1.1.tar.gz" } ], "0.1.2": [ { "comment_text": "", "digests": { "md5": "c271dad473743812ae1a8c3f72473e97", "sha256": "3b66f5c8e979228cdbc5409a0d713b2bffeb1c6d912fd6657d7f34f9f0548e25" }, "downloads": -1, "filename": "meeshkan-0.1.2-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "c271dad473743812ae1a8c3f72473e97", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 38673, "upload_time": "2018-12-04T11:20:34", "url": "https://files.pythonhosted.org/packages/35/6e/a926914dc2511036da0df854160d7b7c9d24220446a532139ca0e46e3ef0/meeshkan-0.1.2-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "e2ca45f7c371de060255b68b4da97d5a", "sha256": "0b8f4ddf0af458bf7019f92173d38de9551c738e3fd530fafd9a483f8d7750c2" }, "downloads": -1, "filename": "meeshkan-0.1.2.tar.gz", "has_sig": false, "md5_digest": "e2ca45f7c371de060255b68b4da97d5a", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 33486, "upload_time": "2018-12-04T11:20:35", "url": "https://files.pythonhosted.org/packages/1f/03/2031c082e61abd676378406df6dae90c0b378790b0fb2c44ab074b91ed46/meeshkan-0.1.2.tar.gz" } ], "0.1.3": [ { "comment_text": "", "digests": { "md5": "61f4d9ca7ce8e4b1a7d212cd72f61ed7", "sha256": "aca9167f217b8ecb22e611eeeaff10540ca842efde052ad64c4a13cdfdaf6b22" }, "downloads": -1, "filename": "meeshkan-0.1.3-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "61f4d9ca7ce8e4b1a7d212cd72f61ed7", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 41691, "upload_time": "2019-01-09T08:31:43", "url": "https://files.pythonhosted.org/packages/76/5c/f9043bc7d11e24fa029406525619ec74352ae5be3267d6e3f7316b8665d0/meeshkan-0.1.3-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "25e4168e1561ee96644ce872d8af7198", "sha256": "f1b5db471b6c7efcebcff763e9bc51d94d44f16ad5256de650fd9ec2d8a53deb" }, "downloads": -1, "filename": "meeshkan-0.1.3.tar.gz", "has_sig": false, "md5_digest": "25e4168e1561ee96644ce872d8af7198", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 37880, "upload_time": "2019-01-09T08:31:45", "url": "https://files.pythonhosted.org/packages/d4/4f/8d8054a86831caa1086dd99684858536e6fba12eb4700152fc1c4d6946ea/meeshkan-0.1.3.tar.gz" } ], "0.1.4": [ { "comment_text": "", "digests": { "md5": "3848047e195ad027ace7094284acd1d1", "sha256": "69ab8e4af5c10133afc58b7dafb25520773adce55cfec25ad7f3f217175d1acf" }, "downloads": -1, "filename": "meeshkan-0.1.4-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "3848047e195ad027ace7094284acd1d1", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 49479, "upload_time": "2019-01-16T09:41:48", "url": "https://files.pythonhosted.org/packages/c4/a9/fb684f47bd67e4270aa9727292dc2c976e1ebe028d4f7c2511fffcd33ce9/meeshkan-0.1.4-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "eba3d5b145a072e698f88266d24a4ab9", "sha256": "5e78911a98df4e300ad3659f5261d294066678747a5872bb94826e86b800af1d" }, "downloads": -1, "filename": "meeshkan-0.1.4.tar.gz", "has_sig": false, "md5_digest": "eba3d5b145a072e698f88266d24a4ab9", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 43122, "upload_time": "2019-01-16T09:41:50", "url": "https://files.pythonhosted.org/packages/6c/ec/7b721d05ca90b82712c700798f94dea8bb3046cb1dfec3d29b12acc4bfce/meeshkan-0.1.4.tar.gz" } ], "0.1.5": [ { "comment_text": "", "digests": { "md5": "77f9eb228f1149bd7ff0cc2f76471287", "sha256": "9ad9848c58aaa35d03a912ceab672f33b283c49bb96c6257ff058a0905388231" }, "downloads": -1, "filename": "meeshkan-0.1.5-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "77f9eb228f1149bd7ff0cc2f76471287", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 59070, "upload_time": "2019-01-25T07:53:50", "url": "https://files.pythonhosted.org/packages/ba/c4/70242049b96c4347928fe2b10cbfcf3326488baae99b2af81465e003196f/meeshkan-0.1.5-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "b51f9ccb3a831d54e342a24f8bd25b62", "sha256": "51804c910833d5d3b1e3d8e63d01b2aeb378bc7957512ef24f58fba7722dcb40" }, "downloads": -1, "filename": "meeshkan-0.1.5.tar.gz", "has_sig": false, "md5_digest": "b51f9ccb3a831d54e342a24f8bd25b62", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 49968, "upload_time": "2019-01-25T07:53:52", "url": "https://files.pythonhosted.org/packages/95/7a/fd73a5c1694629e6687139063394377d05672202997a4dff78f7e70311ce/meeshkan-0.1.5.tar.gz" } ], "0.1.6": [ { "comment_text": "", "digests": { "md5": "d0a12cb9fb8ad20a6c0b2371b81d937e", "sha256": "0bc5c7c17ec52a4e6830f08586767b4b8860f8074d0b489f0e0f6ac2c0b42dba" }, "downloads": -1, "filename": "meeshkan-0.1.6-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "d0a12cb9fb8ad20a6c0b2371b81d937e", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 65253, "upload_time": "2019-02-06T08:58:40", "url": "https://files.pythonhosted.org/packages/44/be/384a772806e3dd636bec23ebb48f4f93d80d3df821a7ef2b56ef40f3cf31/meeshkan-0.1.6-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "f18172c9b287cc7b601bc8ea2dae4055", "sha256": "d8817b5b295714e97c24c7d3798c366892972622fbafbbceeae71072b2d5360d" }, "downloads": -1, "filename": "meeshkan-0.1.6.tar.gz", "has_sig": false, "md5_digest": "f18172c9b287cc7b601bc8ea2dae4055", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 56020, "upload_time": "2019-02-06T08:58:42", "url": "https://files.pythonhosted.org/packages/83/5f/e2a8574eb4910b75d3a32ccb7ff26093409a7ba892323677dc1a7d1af9a6/meeshkan-0.1.6.tar.gz" } ], "0.1.7": [ { "comment_text": "", "digests": { "md5": "698fc7db812e8c78354c90a6486a51a8", "sha256": "29a17b3d038af3dee1eccc1cb68149980ffe6b615c14431e73a19b79b97f42ae" }, "downloads": -1, "filename": "meeshkan-0.1.7-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "698fc7db812e8c78354c90a6486a51a8", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 65415, "upload_time": "2019-02-27T08:53:00", "url": "https://files.pythonhosted.org/packages/7b/9c/7dc11a0b354deb8b8a3c0cfb9c842bbebf81a9db90d63d675d1b958c16fd/meeshkan-0.1.7-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "985d0f0271ffd16d01b5d1cd589e2003", "sha256": "f777bda769c7a6236c13a5a60289c2a099c8f928909a24b953069adbf8775f25" }, "downloads": -1, "filename": "meeshkan-0.1.7.tar.gz", "has_sig": false, "md5_digest": "985d0f0271ffd16d01b5d1cd589e2003", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 56188, "upload_time": "2019-02-27T08:53:02", "url": "https://files.pythonhosted.org/packages/e6/8f/78f34d5d5bd6b7f57410bc1f62efbd37ab4d4a19ba5cd22e5087845825b0/meeshkan-0.1.7.tar.gz" } ], "0.1.8": [ { "comment_text": "", "digests": { "md5": "7e9dae355a6aec2bade8212fbbee12b2", "sha256": "4a9493a2b3e2f95c1a5e4e170462749383eeca269d0b0cf3e0ec09022968ee17" }, "downloads": -1, "filename": "meeshkan-0.1.8-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "7e9dae355a6aec2bade8212fbbee12b2", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 67063, "upload_time": "2019-03-08T11:23:11", "url": "https://files.pythonhosted.org/packages/1f/7e/e36165010ad1cbd44c01fb556f23905197f4d88ebb888c10c5377c0b9a51/meeshkan-0.1.8-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "e820f7cbfdcb508840786e1ce2041c51", "sha256": "bf1b032942e36a482bb3c2857b53308cdb350148c1a1152ea424298de9876498" }, "downloads": -1, "filename": "meeshkan-0.1.8.tar.gz", "has_sig": false, "md5_digest": "e820f7cbfdcb508840786e1ce2041c51", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 58036, "upload_time": "2019-03-08T11:23:13", "url": "https://files.pythonhosted.org/packages/e5/8b/bf3083f526fe46a6f22d91e707443d167298f5213ac27df5990f6486c557/meeshkan-0.1.8.tar.gz" } ], "0.1.9": [ { "comment_text": "", "digests": { "md5": "c92ea3f0a3f0a9052d5fdde071082e50", "sha256": "dd4d7750ff4d6b881525f6a939e4e0cb88f4c7517c1a06a60e2dbddab2b90481" }, "downloads": -1, "filename": "meeshkan-0.1.9-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "c92ea3f0a3f0a9052d5fdde071082e50", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 67098, "upload_time": "2019-03-08T12:54:14", "url": "https://files.pythonhosted.org/packages/65/e5/c0ec364102ce07cc06c5274b619e2d08e4797348fb7292b4784998da4768/meeshkan-0.1.9-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "d668ddbd8af31c527a78c8cc6ce73965", "sha256": "7e4164fc8279a0d702fdf05c182f07a16f20d89c0d9d91f7e15b3386a83262e5" }, "downloads": -1, "filename": "meeshkan-0.1.9.tar.gz", "has_sig": false, "md5_digest": "d668ddbd8af31c527a78c8cc6ce73965", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 58042, "upload_time": "2019-03-08T12:54:15", "url": "https://files.pythonhosted.org/packages/b9/1e/18abc0e33b51ce45cbdd7fb780b6c38a6558041f11f1bd72eb3706a2c2c6/meeshkan-0.1.9.tar.gz" } ] }, "urls": [ { "comment_text": "", "digests": { "md5": "c92ea3f0a3f0a9052d5fdde071082e50", "sha256": "dd4d7750ff4d6b881525f6a939e4e0cb88f4c7517c1a06a60e2dbddab2b90481" }, "downloads": -1, "filename": "meeshkan-0.1.9-py2.py3-none-any.whl", "has_sig": false, "md5_digest": "c92ea3f0a3f0a9052d5fdde071082e50", "packagetype": "bdist_wheel", "python_version": "py2.py3", "requires_python": ">=3.6.0", "size": 67098, "upload_time": "2019-03-08T12:54:14", "url": "https://files.pythonhosted.org/packages/65/e5/c0ec364102ce07cc06c5274b619e2d08e4797348fb7292b4784998da4768/meeshkan-0.1.9-py2.py3-none-any.whl" }, { "comment_text": "", "digests": { "md5": "d668ddbd8af31c527a78c8cc6ce73965", "sha256": "7e4164fc8279a0d702fdf05c182f07a16f20d89c0d9d91f7e15b3386a83262e5" }, "downloads": -1, "filename": "meeshkan-0.1.9.tar.gz", "has_sig": false, "md5_digest": "d668ddbd8af31c527a78c8cc6ce73965", "packagetype": "sdist", "python_version": "source", "requires_python": ">=3.6.0", "size": 58042, "upload_time": "2019-03-08T12:54:15", "url": "https://files.pythonhosted.org/packages/b9/1e/18abc0e33b51ce45cbdd7fb780b6c38a6558041f11f1bd72eb3706a2c2c6/meeshkan-0.1.9.tar.gz" } ] }