Join threads or else the number of running threads increments by 5 at each request and will never stop until main process is killed

--- source/views.py
+++ source/views.py
@@ -17,12 +17,14 @@
             async_tech_specs = pool.apply_async(view_models.get_tech_spec, (title,))
             async_price = pool.apply_async(view_models.get_price, (title,))
             async_artwork = pool.apply_async(view_models.get_artwork, (title,))
+            pool.close()

             rt_rating = async_rt_rating.get()
             bluray_rating = async_bluray_rating.get()
             tech_specs = async_tech_specs.get()
             price = async_price.get()
             artwork = async_artwork.get()
+            pool.join()

             return render(request, 'index.html', {'form': form, 'rt_rating': rt_rating, 'bluray_rating': bluray_rating, 'tech_specs': tech_specs, 'price': price, 'artwork': artwork})

<|original_code|>
from multiprocessing.pool import ThreadPool
from django.shortcuts import render
from .forms import SearchForm
from source import view_models

def index(request):
    if request.method == 'GET':
        form = SearchForm(request.GET)

        if form.is_valid():
            title = request.GET.__getitem__('movie_title').__str__()

            pool = ThreadPool(processes=5)
            async_rt_rating = pool.apply_async(view_models.get_rt_rating, (title,))
            async_bluray_rating = pool.apply_async(view_models.get_bluray_rating, (title,))
            async_tech_specs = pool.apply_async(view_models.get_tech_spec, (title,))
            async_price = pool.apply_async(view_models.get_price, (title,))
            async_artwork = pool.apply_async(view_models.get_artwork, (title,))

            rt_rating = async_rt_rating.get()
            bluray_rating = async_bluray_rating.get()
            tech_specs = async_tech_specs.get()
            price = async_price.get()
            artwork = async_artwork.get()

            return render(request, 'index.html', {'form': form, 'rt_rating': rt_rating, 'bluray_rating': bluray_rating, 'tech_specs': tech_specs, 'price': price, 'artwork': artwork})

    else:
        form = SearchForm()

    return render(request, 'index.html', {'form': form})

<|edits_diff|>
--- source/views.py
+++ source/views.py
@@ -17,6 +17,7 @@
             async_tech_specs = pool.apply_async(view_models.get_tech_spec, (title,))
             async_price = pool.apply_async(view_models.get_price, (title,))
             async_artwork = pool.apply_async(view_models.get_artwork, (title,))
+            pool.close()

             rt_rating = async_rt_rating.get()
             bluray_rating = async_bluray_rating.get()
<|current_version|>
from multiprocessing.pool import ThreadPool
from django.shortcuts import render
from .forms import SearchForm
from source import view_models

def index(request):
    if request.method == 'GET':
        form = SearchForm(request.GET)

        if form.is_valid():
            title = request.GET.__getitem__('movie_title').__str__()

            pool = ThreadPool(processes=5)
            async_rt_rating = pool.apply_async(view_models.get_rt_rating, (title,))
            async_bluray_rating = pool.apply_async(view_models.get_bluray_rating, (title,))
            async_tech_specs = pool.apply_async(view_models.get_tech_spec, (title,))
            async_price = pool.apply_async(view_models.get_price, (title,))
            async_artwork = pool.apply_async(view_models.get_artwork, (title,))
            pool.close()

            rt_rating = async_rt_rating.get()
            bluray_rating = async_bluray_rating.get()
            tech_specs = async_tech_specs.get()
            price = async_price.get()
            artwork = async_artwork.get()

            return render(request, 'index.html', {'form': form, 'rt_rating': rt_rating, 'bluray_rating': bluray_rating, 'tech_specs': tech_specs, 'price': price, 'artwork': artwork})

    else:
        form = SearchForm()

    return render(request, 'index.html', {'form': form})

<|next_version|>
from multiprocessing.pool import ThreadPool
from django.shortcuts import render
from .forms import SearchForm
from source import view_models

def index(request):
    if request.method == 'GET':
        form = SearchForm(request.GET)

        if form.is_valid():
            title = request.GET.__getitem__('movie_title').__str__()

            pool = ThreadPool(processes=5)
            async_rt_rating = pool.apply_async(view_models.get_rt_rating, (title,))
            async_bluray_rating = pool.apply_async(view_models.get_bluray_rating, (title,))
            async_tech_specs = pool.apply_async(view_models.get_tech_spec, (title,))
            async_price = pool.apply_async(view_models.get_price, (title,))
            async_artwork = pool.apply_async(view_models.get_artwork, (title,))
            pool.close()

            rt_rating = async_rt_rating.get()
            bluray_rating = async_bluray_rating.get()
            tech_specs = async_tech_specs.get()
            price = async_price.get()
            artwork = async_artwork.get()
            pool.join()

            return render(request, 'index.html', {'form': form, 'rt_rating': rt_rating, 'bluray_rating': bluray_rating, 'tech_specs': tech_specs, 'price': price, 'artwork': artwork})

    else:
        form = SearchForm()

    return render(request, 'index.html', {'form': form})


Fix last code quality issues

Fix last code quality issues

--- tests/test_views.py
+++ tests/test_views.py
@@ -14,6 +14,7 @@
     @patch('app.views.notify_recipient')
     @patch('app.views.is_valid_pull_request')
     def test_valid_pull_request(self, validator, notifier):
+        """ Should notify upon a valid pull request. """
         validator.return_value = True
         notifier.return_value = True
         result = views.pull_request({}, None)
@@ -21,6 +22,7 @@

     @patch('app.views.is_valid_pull_request')
     def test_invalid_pull_request(self, validator):
+        """ Should ignore an invalid pull request. """
         validator.return_value = False
         result = views.pull_request({}, None)
         self.assertRegex(result, 'ignored')

<|original_code|>
""" Tests for the main server file. """
from unittest import TestCase
from unittest.mock import patch

from app import views

class ViewsTestCase(TestCase):
    """ Our main server testcase. """

    def test_ping(self):
        self.assertEqual(views.ping(None, None), 'pong')

    @patch('app.views.notify_recipient')
    @patch('app.views.is_valid_pull_request')
    def test_valid_pull_request(self, validator, notifier):
        validator.return_value = True
        notifier.return_value = True
        result = views.pull_request({}, None)
        self.assertEqual(result, 'Recipient Notified')

    @patch('app.views.is_valid_pull_request')
    def test_invalid_pull_request(self, validator):
        validator.return_value = False
        result = views.pull_request({}, None)
        self.assertRegex(result, 'ignored')

<|edits_diff|>
--- tests/test_views.py
+++ tests/test_views.py
@@ -14,6 +14,7 @@
     @patch('app.views.notify_recipient')
     @patch('app.views.is_valid_pull_request')
     def test_valid_pull_request(self, validator, notifier):
+        """ Should notify upon a valid pull request. """
         validator.return_value = True
         notifier.return_value = True
         result = views.pull_request({}, None)
<|current_version|>
""" Tests for the main server file. """
from unittest import TestCase
from unittest.mock import patch

from app import views

class ViewsTestCase(TestCase):
    """ Our main server testcase. """

    def test_ping(self):
        self.assertEqual(views.ping(None, None), 'pong')

    @patch('app.views.notify_recipient')
    @patch('app.views.is_valid_pull_request')
    def test_valid_pull_request(self, validator, notifier):
        """ Should notify upon a valid pull request. """
        validator.return_value = True
        notifier.return_value = True
        result = views.pull_request({}, None)
        self.assertEqual(result, 'Recipient Notified')

    @patch('app.views.is_valid_pull_request')
    def test_invalid_pull_request(self, validator):
        validator.return_value = False
        result = views.pull_request({}, None)
        self.assertRegex(result, 'ignored')

<|next_version|>
""" Tests for the main server file. """
from unittest import TestCase
from unittest.mock import patch

from app import views

class ViewsTestCase(TestCase):
    """ Our main server testcase. """

    def test_ping(self):
        self.assertEqual(views.ping(None, None), 'pong')

    @patch('app.views.notify_recipient')
    @patch('app.views.is_valid_pull_request')
    def test_valid_pull_request(self, validator, notifier):
        """ Should notify upon a valid pull request. """
        validator.return_value = True
        notifier.return_value = True
        result = views.pull_request({}, None)
        self.assertEqual(result, 'Recipient Notified')

    @patch('app.views.is_valid_pull_request')
    def test_invalid_pull_request(self, validator):
        """ Should ignore an invalid pull request. """
        validator.return_value = False
        result = views.pull_request({}, None)
        self.assertRegex(result, 'ignored')


Make fields required on new client and company

--- estmator_project/est_client/forms.py
+++ estmator_project/est_client/forms.py
@@ -16,6 +16,11 @@
         ]
         widgets = {
             'company': Select(attrs={'required': True}),
+            'first_name': TextInput(attrs={'required': True}),
+            'last_name': TextInput(attrs={'required': True}),
+            'title': TextInput(attrs={'required': True}),
+            'cell': TextInput(attrs={'required': True}),
+            'email': TextInput(attrs={'required': True}),
         }

@@ -35,6 +40,10 @@
         ]
         widgets = {
             'company_name': TextInput(attrs={'required': True}),
+            'phone': TextInput(attrs={'required': True}),
+            'address': TextInput(attrs={'required': True}),
+            'city': TextInput(attrs={'required': True}),
+            'postal': TextInput(attrs={'required': True}),
         }

<|original_code|>
from django.forms import ModelForm, Select, TextInput
from .models import Client, Company

class ClientCreateForm(ModelForm):
    class Meta:
        model = Client
        fields = [
            'company',
            'first_name',
            'last_name',
            'title',
            'cell',
            'desk',
            'email'
        ]
        widgets = {
            'company': Select(attrs={'required': True}),
        }

class CompanyCreateForm(ModelForm):
    class Meta:
        model = Company
        fields = [
            'company_name',
            'phone',
            'address',
            'address2',
            'city',
            'state',
            'postal',
            'st_rate',
            'ot_rate'
        ]
        widgets = {
            'company_name': TextInput(attrs={'required': True}),
        }

class CompanyListForm(ModelForm):
    class Meta:
        model = Client
        fields = ['company']

<|edits_diff|>
--- estmator_project/est_client/forms.py
+++ estmator_project/est_client/forms.py
@@ -16,6 +16,11 @@
         ]
         widgets = {
             'company': Select(attrs={'required': True}),
+            'first_name': TextInput(attrs={'required': True}),
+            'last_name': TextInput(attrs={'required': True}),
+            'title': TextInput(attrs={'required': True}),
+            'cell': TextInput(attrs={'required': True}),
+            'email': TextInput(attrs={'required': True}),
         }

<|current_version|>
from django.forms import ModelForm, Select, TextInput
from .models import Client, Company

class ClientCreateForm(ModelForm):
    class Meta:
        model = Client
        fields = [
            'company',
            'first_name',
            'last_name',
            'title',
            'cell',
            'desk',
            'email'
        ]
        widgets = {
            'company': Select(attrs={'required': True}),
            'first_name': TextInput(attrs={'required': True}),
            'last_name': TextInput(attrs={'required': True}),
            'title': TextInput(attrs={'required': True}),
            'cell': TextInput(attrs={'required': True}),
            'email': TextInput(attrs={'required': True}),
        }

class CompanyCreateForm(ModelForm):
    class Meta:
        model = Company
        fields = [
            'company_name',
            'phone',
            'address',
            'address2',
            'city',
            'state',
            'postal',
            'st_rate',
            'ot_rate'
        ]
        widgets = {
            'company_name': TextInput(attrs={'required': True}),
        }

class CompanyListForm(ModelForm):
    class Meta:
        model = Client
        fields = ['company']

<|next_version|>
from django.forms import ModelForm, Select, TextInput
from .models import Client, Company

class ClientCreateForm(ModelForm):
    class Meta:
        model = Client
        fields = [
            'company',
            'first_name',
            'last_name',
            'title',
            'cell',
            'desk',
            'email'
        ]
        widgets = {
            'company': Select(attrs={'required': True}),
            'first_name': TextInput(attrs={'required': True}),
            'last_name': TextInput(attrs={'required': True}),
            'title': TextInput(attrs={'required': True}),
            'cell': TextInput(attrs={'required': True}),
            'email': TextInput(attrs={'required': True}),
        }

class CompanyCreateForm(ModelForm):
    class Meta:
        model = Company
        fields = [
            'company_name',
            'phone',
            'address',
            'address2',
            'city',
            'state',
            'postal',
            'st_rate',
            'ot_rate'
        ]
        widgets = {
            'company_name': TextInput(attrs={'required': True}),
            'phone': TextInput(attrs={'required': True}),
            'address': TextInput(attrs={'required': True}),
            'city': TextInput(attrs={'required': True}),
            'postal': TextInput(attrs={'required': True}),
        }

class CompanyListForm(ModelForm):
    class Meta:
        model = Client
        fields = ['company']


Allow Google AppEngine Memcache stub to be used for running unit tests including calls to caching layer

--- src/tests/ggrc/__init__.py
+++ src/tests/ggrc/__init__.py
@@ -7,16 +7,22 @@
 from ggrc import db
 from ggrc.app import app
 from ggrc.models import create_db, drop_db
+from google.appengine.api import memcache
+from google.appengine.ext import testbed

 use_migrations = False

 class TestCase(BaseTestCase):
   def setUp(self):
     create_db(use_migrations, quiet=True)
+    self.testbed = testbed.Testbed()
+    self.testbed.activate()
+    self.testbed.init_memcache_stub()

   def tearDown(self):
     db.session.remove()
     drop_db(use_migrations, quiet=True)
+    self.testbed.deactivate()

   def create_app(self):
     app.testing = True

<|original_code|>
# Copyright (C) 2013 Google Inc., authors, and contributors <see AUTHORS file>
# Licensed under http://www.apache.org/licenses/LICENSE-2.0 <see LICENSE file>
# Created By: david@reciprocitylabs.com
# Maintained By: david@reciprocitylabs.com

from flask.ext.testing import TestCase as BaseTestCase
from ggrc import db
from ggrc.app import app
from ggrc.models import create_db, drop_db

use_migrations = False

class TestCase(BaseTestCase):
  def setUp(self):
    create_db(use_migrations, quiet=True)

  def tearDown(self):
    db.session.remove()
    drop_db(use_migrations, quiet=True)

  def create_app(self):
    app.testing = True
    app.debug = False
    return app

<|edits_diff|>
--- src/tests/ggrc/__init__.py
+++ src/tests/ggrc/__init__.py
@@ -7,12 +7,17 @@
 from ggrc import db
 from ggrc.app import app
 from ggrc.models import create_db, drop_db
+from google.appengine.api import memcache
+from google.appengine.ext import testbed

 use_migrations = False

 class TestCase(BaseTestCase):
   def setUp(self):
     create_db(use_migrations, quiet=True)
+    self.testbed = testbed.Testbed()
+    self.testbed.activate()
+    self.testbed.init_memcache_stub()

   def tearDown(self):
     db.session.remove()
<|current_version|>
# Copyright (C) 2013 Google Inc., authors, and contributors <see AUTHORS file>
# Licensed under http://www.apache.org/licenses/LICENSE-2.0 <see LICENSE file>
# Created By: david@reciprocitylabs.com
# Maintained By: david@reciprocitylabs.com

from flask.ext.testing import TestCase as BaseTestCase
from ggrc import db
from ggrc.app import app
from ggrc.models import create_db, drop_db
from google.appengine.api import memcache
from google.appengine.ext import testbed

use_migrations = False

class TestCase(BaseTestCase):
  def setUp(self):
    create_db(use_migrations, quiet=True)
    self.testbed = testbed.Testbed()
    self.testbed.activate()
    self.testbed.init_memcache_stub()

  def tearDown(self):
    db.session.remove()
    drop_db(use_migrations, quiet=True)

  def create_app(self):
    app.testing = True
    app.debug = False
    return app

<|next_version|>
# Copyright (C) 2013 Google Inc., authors, and contributors <see AUTHORS file>
# Licensed under http://www.apache.org/licenses/LICENSE-2.0 <see LICENSE file>
# Created By: david@reciprocitylabs.com
# Maintained By: david@reciprocitylabs.com

from flask.ext.testing import TestCase as BaseTestCase
from ggrc import db
from ggrc.app import app
from ggrc.models import create_db, drop_db
from google.appengine.api import memcache
from google.appengine.ext import testbed

use_migrations = False

class TestCase(BaseTestCase):
  def setUp(self):
    create_db(use_migrations, quiet=True)
    self.testbed = testbed.Testbed()
    self.testbed.activate()
    self.testbed.init_memcache_stub()

  def tearDown(self):
    db.session.remove()
    drop_db(use_migrations, quiet=True)
    self.testbed.deactivate()

  def create_app(self):
    app.testing = True
    app.debug = False
    return app


Fix pip installs of astropy-helpers

Fix pip installs of astropy-helpers

--- setup.py
+++ setup.py
@@ -4,6 +4,7 @@
 # NOTE: most of the configuration, including the version number,
 # is defined in setup.cfg

+import os
 import sys
 from distutils.version import LooseVersion

@@ -14,6 +15,10 @@
     sys.stderr.write("ERROR: setuptools 30.3 or later is required by astropy-helpers\n")
     sys.exit(1)

+# Need to add current directory to be able to import astropy-helpers
+# despite PEP517/518 build isolation
+sys.path.append(os.path.abspath("."))
+
 from astropy_helpers.version_helpers import generate_version_py  # noqa
 version = generate_version_py()

<|original_code|>
#!/usr/bin/env python
# Licensed under a 3-clause BSD style license - see LICENSE.rst

# NOTE: most of the configuration, including the version number,
# is defined in setup.cfg

import sys
from distutils.version import LooseVersion

import setuptools
from setuptools import setup

if LooseVersion(setuptools.__version__) < '30.3':
    sys.stderr.write("ERROR: setuptools 30.3 or later is required by astropy-helpers\n")
    sys.exit(1)

from astropy_helpers.version_helpers import generate_version_py  # noqa
version = generate_version_py()

setup(version=version)

<|edits_diff|>
--- setup.py
+++ setup.py
@@ -4,6 +4,7 @@
 # NOTE: most of the configuration, including the version number,
 # is defined in setup.cfg

+import os
 import sys
 from distutils.version import LooseVersion

<|current_version|>
#!/usr/bin/env python
# Licensed under a 3-clause BSD style license - see LICENSE.rst

# NOTE: most of the configuration, including the version number,
# is defined in setup.cfg

import os
import sys
from distutils.version import LooseVersion

import setuptools
from setuptools import setup

if LooseVersion(setuptools.__version__) < '30.3':
    sys.stderr.write("ERROR: setuptools 30.3 or later is required by astropy-helpers\n")
    sys.exit(1)

from astropy_helpers.version_helpers import generate_version_py  # noqa
version = generate_version_py()

setup(version=version)

<|next_version|>
#!/usr/bin/env python
# Licensed under a 3-clause BSD style license - see LICENSE.rst

# NOTE: most of the configuration, including the version number,
# is defined in setup.cfg

import os
import sys
from distutils.version import LooseVersion

import setuptools
from setuptools import setup

if LooseVersion(setuptools.__version__) < '30.3':
    sys.stderr.write("ERROR: setuptools 30.3 or later is required by astropy-helpers\n")
    sys.exit(1)

# Need to add current directory to be able to import astropy-helpers
# despite PEP517/518 build isolation
sys.path.append(os.path.abspath("."))

from astropy_helpers.version_helpers import generate_version_py  # noqa
version = generate_version_py()

setup(version=version)


Configure nova.flags as well as openstack.common.cfg

Because we are using nova classes directly (Service, Manager, etc.)
we need to initialize the configuration modules that those
classes use.

Change-Id: Idafd4a8346fc59332114ea7536893470bf9eaff8

--- ceilometer/service.py
+++ ceilometer/service.py
@@ -17,6 +17,8 @@
 # License for the specific language governing permissions and limitations
 # under the License.

+from nova import flags
+
 from ceilometer import log
 from ceilometer.openstack.common import cfg

@@ -29,4 +31,9 @@

 def prepare_service(argv=[]):
     cfg.CONF(argv[1:])
+    # FIXME(dhellmann): We must set up the nova.flags module in order
+    # to have the RPC and DB access work correctly because we are
+    # still using the Service object out of nova directly. We need to
+    # move that into openstack.common.
+    flags.FLAGS(argv[1:])
     log.setup()

<|original_code|>
#!/usr/bin/env python
# -*- encoding: utf-8 -*-
#
# Copyright © 2012 eNovance <licensing@enovance.com>
#
# Author: Julien Danjou <julien@danjou.info>
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.

from ceilometer import log
from ceilometer.openstack.common import cfg

cfg.CONF.register_opts([
    cfg.IntOpt('periodic_interval',
               default=60,
               help='seconds between running periodic tasks')
])

def prepare_service(argv=[]):
    cfg.CONF(argv[1:])
    log.setup()

<|edits_diff|>
--- ceilometer/service.py
+++ ceilometer/service.py
@@ -17,6 +17,8 @@
 # License for the specific language governing permissions and limitations
 # under the License.

+from nova import flags
+
 from ceilometer import log
 from ceilometer.openstack.common import cfg

<|current_version|>
#!/usr/bin/env python
# -*- encoding: utf-8 -*-
#
# Copyright © 2012 eNovance <licensing@enovance.com>
#
# Author: Julien Danjou <julien@danjou.info>
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.

from nova import flags

from ceilometer import log
from ceilometer.openstack.common import cfg

cfg.CONF.register_opts([
    cfg.IntOpt('periodic_interval',
               default=60,
               help='seconds between running periodic tasks')
])

def prepare_service(argv=[]):
    cfg.CONF(argv[1:])
    log.setup()

<|next_version|>
#!/usr/bin/env python
# -*- encoding: utf-8 -*-
#
# Copyright © 2012 eNovance <licensing@enovance.com>
#
# Author: Julien Danjou <julien@danjou.info>
#
# Licensed under the Apache License, Version 2.0 (the "License"); you may
# not use this file except in compliance with the License. You may obtain
# a copy of the License at
#
#      http://www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing, software
# distributed under the License is distributed on an "AS IS" BASIS, WITHOUT
# WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the
# License for the specific language governing permissions and limitations
# under the License.

from nova import flags

from ceilometer import log
from ceilometer.openstack.common import cfg

cfg.CONF.register_opts([
    cfg.IntOpt('periodic_interval',
               default=60,
               help='seconds between running periodic tasks')
])

def prepare_service(argv=[]):
    cfg.CONF(argv[1:])
    # FIXME(dhellmann): We must set up the nova.flags module in order
    # to have the RPC and DB access work correctly because we are
    # still using the Service object out of nova directly. We need to
    # move that into openstack.common.
    flags.FLAGS(argv[1:])
    log.setup()


Raise TypeError if positional batchable argument is missing

e.g. if it's erroneously been passed as a named argument.

--- panoptes_client/utils.py
+++ panoptes_client/utils.py
@@ -9,6 +9,8 @@
     set,
     tuple,
 )
+
+MISSING_POSITIONAL_ERR = 'Required positional argument (pos 1) not found'

 try:
     from numpy import ndarray
@@ -23,12 +25,17 @@

 def batchable(func=None, batch_size=100):
     def do_batch(*args, **kwargs):
+        if len(args) == 0:
+            raise TypeError(MISSING_POSITIONAL_ERR)
         _batch_size = kwargs.pop('batch_size', batch_size)
+
         if isiterable(args[0]):
             _self = None
             to_batch = args[0]
             args = args[1:]
         else:
+            if len(args) == 1:
+                raise TypeError(MISSING_POSITIONAL_ERR)
             _self = args[0]
             to_batch = args[1]
             args = args[2:]

<|original_code|>
from __future__ import absolute_import, division, print_function
from builtins import range

import functools

ITERABLE_TYPES = (
    list,
    set,
    tuple,
)

try:
    from numpy import ndarray
    ITERABLE_TYPES = ITERABLE_TYPES + (ndarray,)
except ImportError:
    pass

def isiterable(v):
    return isinstance(v, ITERABLE_TYPES)

def batchable(func=None, batch_size=100):
    def do_batch(*args, **kwargs):
        _batch_size = kwargs.pop('batch_size', batch_size)
        if isiterable(args[0]):
            _self = None
            to_batch = args[0]
            args = args[1:]
        else:
            _self = args[0]
            to_batch = args[1]
            args = args[2:]
            if not isiterable(to_batch):
                to_batch = [to_batch]

        if isinstance(to_batch, set):
            to_batch = list(to_batch)

        for _batch in [
            to_batch[i:i+_batch_size]
            for i in range(0, len(to_batch), _batch_size)
        ]:
            if _self is None:
                func(_batch, *args, **kwargs)
            else:
                func(_self, _batch, *args, **kwargs)

    if func is None:
        return functools.partial(batchable, batch_size=batch_size)
    return do_batch

<|edits_diff|>
--- panoptes_client/utils.py
+++ panoptes_client/utils.py
@@ -9,6 +9,8 @@
     set,
     tuple,
 )
+
+MISSING_POSITIONAL_ERR = 'Required positional argument (pos 1) not found'

 try:
     from numpy import ndarray
@@ -23,7 +25,10 @@

 def batchable(func=None, batch_size=100):
     def do_batch(*args, **kwargs):
+        if len(args) == 0:
+            raise TypeError(MISSING_POSITIONAL_ERR)
         _batch_size = kwargs.pop('batch_size', batch_size)
+
         if isiterable(args[0]):
             _self = None
             to_batch = args[0]
<|current_version|>
from __future__ import absolute_import, division, print_function
from builtins import range

import functools

ITERABLE_TYPES = (
    list,
    set,
    tuple,
)

MISSING_POSITIONAL_ERR = 'Required positional argument (pos 1) not found'

try:
    from numpy import ndarray
    ITERABLE_TYPES = ITERABLE_TYPES + (ndarray,)
except ImportError:
    pass

def isiterable(v):
    return isinstance(v, ITERABLE_TYPES)

def batchable(func=None, batch_size=100):
    def do_batch(*args, **kwargs):
        if len(args) == 0:
            raise TypeError(MISSING_POSITIONAL_ERR)
        _batch_size = kwargs.pop('batch_size', batch_size)

        if isiterable(args[0]):
            _self = None
            to_batch = args[0]
            args = args[1:]
        else:
            _self = args[0]
            to_batch = args[1]
            args = args[2:]
            if not isiterable(to_batch):
                to_batch = [to_batch]

        if isinstance(to_batch, set):
            to_batch = list(to_batch)

        for _batch in [
            to_batch[i:i+_batch_size]
            for i in range(0, len(to_batch), _batch_size)
        ]:
            if _self is None:
                func(_batch, *args, **kwargs)
            else:
                func(_self, _batch, *args, **kwargs)

    if func is None:
        return functools.partial(batchable, batch_size=batch_size)
    return do_batch

<|next_version|>
from __future__ import absolute_import, division, print_function
from builtins import range

import functools

ITERABLE_TYPES = (
    list,
    set,
    tuple,
)

MISSING_POSITIONAL_ERR = 'Required positional argument (pos 1) not found'

try:
    from numpy import ndarray
    ITERABLE_TYPES = ITERABLE_TYPES + (ndarray,)
except ImportError:
    pass

def isiterable(v):
    return isinstance(v, ITERABLE_TYPES)

def batchable(func=None, batch_size=100):
    def do_batch(*args, **kwargs):
        if len(args) == 0:
            raise TypeError(MISSING_POSITIONAL_ERR)
        _batch_size = kwargs.pop('batch_size', batch_size)

        if isiterable(args[0]):
            _self = None
            to_batch = args[0]
            args = args[1:]
        else:
            if len(args) == 1:
                raise TypeError(MISSING_POSITIONAL_ERR)
            _self = args[0]
            to_batch = args[1]
            args = args[2:]
            if not isiterable(to_batch):
                to_batch = [to_batch]

        if isinstance(to_batch, set):
            to_batch = list(to_batch)

        for _batch in [
            to_batch[i:i+_batch_size]
            for i in range(0, len(to_batch), _batch_size)
        ]:
            if _self is None:
                func(_batch, *args, **kwargs)
            else:
                func(_self, _batch, *args, **kwargs)

    if func is None:
        return functools.partial(batchable, batch_size=batch_size)
    return do_batch


Include Text App in Main

Include Text App in Main

--- src/main.py
+++ src/main.py
@@ -18,6 +18,7 @@
 import program10 as p10
 import program11 as p11
 import program12 as p12
+import program13 as p13

 def main():
     p1.sayhello()
@@ -32,6 +33,7 @@
     p10.launchTopLevelApp()
     p11.launchPanedWindowApp()
     p12.launchNoteBookApp()
+    p13.launchApp()

 if __name__ == '__main__':main()

<|original_code|>
'''
Created on Aug 12, 2017

@author: Aditya

This is the main file and will import other modules/codes written for python tkinter demonstration
'''

import program1 as p1
import program2 as p2
import program3 as p3
import program4 as p4
import program5 as p5
import program6 as p6
import program7 as p7
import program8 as p8
import program9 as p9
import program10 as p10
import program11 as p11
import program12 as p12

def main():
    p1.sayhello()
    p2.HelloAppLaunch()
    p3.GreetingAppLaunch()
    p4.launchButtonApp()
    p5.launchButton2App()
    p6.launchEntryApp()
    p7.launchSimpleCalenderApp()
    p8.ControlledPorgressApp()
    p9.DisplayAppLaunch()
    p10.launchTopLevelApp()
    p11.launchPanedWindowApp()
    p12.launchNoteBookApp()

if __name__ == '__main__':main()

<|edits_diff|>
--- src/main.py
+++ src/main.py
@@ -18,6 +18,7 @@
 import program10 as p10
 import program11 as p11
 import program12 as p12
+import program13 as p13

 def main():
     p1.sayhello()
<|current_version|>
'''
Created on Aug 12, 2017

@author: Aditya

This is the main file and will import other modules/codes written for python tkinter demonstration
'''

import program1 as p1
import program2 as p2
import program3 as p3
import program4 as p4
import program5 as p5
import program6 as p6
import program7 as p7
import program8 as p8
import program9 as p9
import program10 as p10
import program11 as p11
import program12 as p12
import program13 as p13

def main():
    p1.sayhello()
    p2.HelloAppLaunch()
    p3.GreetingAppLaunch()
    p4.launchButtonApp()
    p5.launchButton2App()
    p6.launchEntryApp()
    p7.launchSimpleCalenderApp()
    p8.ControlledPorgressApp()
    p9.DisplayAppLaunch()
    p10.launchTopLevelApp()
    p11.launchPanedWindowApp()
    p12.launchNoteBookApp()

if __name__ == '__main__':main()

<|next_version|>
'''
Created on Aug 12, 2017

@author: Aditya

This is the main file and will import other modules/codes written for python tkinter demonstration
'''

import program1 as p1
import program2 as p2
import program3 as p3
import program4 as p4
import program5 as p5
import program6 as p6
import program7 as p7
import program8 as p8
import program9 as p9
import program10 as p10
import program11 as p11
import program12 as p12
import program13 as p13

def main():
    p1.sayhello()
    p2.HelloAppLaunch()
    p3.GreetingAppLaunch()
    p4.launchButtonApp()
    p5.launchButton2App()
    p6.launchEntryApp()
    p7.launchSimpleCalenderApp()
    p8.ControlledPorgressApp()
    p9.DisplayAppLaunch()
    p10.launchTopLevelApp()
    p11.launchPanedWindowApp()
    p12.launchNoteBookApp()
    p13.launchApp()

if __name__ == '__main__':main()


Add absolute URLs to form and question admin

--- customforms/models.py
+++ customforms/models.py
@@ -1,6 +1,7 @@
 #!/usr/bin/python
 # -*- coding: utf-8 -*-

+from django.core.urlresolvers import reverse
 from django.utils.translation import ugettext as _
 from django.db import models

@@ -14,6 +15,8 @@
     class Meta:
         ordering = ('title', )

+    def get_absolute_url(self):
+        return reverse('customforms.views.view_form', args=[str(self.id)])

 class Question(models.Model):
     form = models.ForeignKey(Form)
@@ -37,6 +40,9 @@
     class Meta:
         ordering = ('form', 'position', )

+    def get_absolute_url(self):
+        return reverse('customforms.views.view_form', args=[str(self.form.id)])
+

 class Choice(models.Model):
     question = models.ForeignKey(Question)

<|original_code|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from django.utils.translation import ugettext as _
from django.db import models

class Form(models.Model):
    title = models.CharField(_("Title"), max_length=255)

    def __unicode__(self):
        return u'%s' % self.title

    class Meta:
        ordering = ('title', )

class Question(models.Model):
    form = models.ForeignKey(Form)
    title = models.CharField(
        _("Title"), max_length=255, default=_("Question Title"))
    help_text = models.TextField(blank=True, null=True)
    CHOICES = [
        ('C', _('Checkbox')),
        ('R', _('Radio')),
        ('S', _('Select')),
        ('T', _('Text')),
        ]
    question_type = models.CharField(
        max_length=1, choices=CHOICES, default="T")
    required = models.BooleanField(default=False)
    position = models.PositiveIntegerField(default=0)

    def __unicode__(self):
        return u'%s' % (self.title, )

    class Meta:
        ordering = ('form', 'position', )

class Choice(models.Model):
    question = models.ForeignKey(Question)
    title = models.CharField(max_length=200,)
    position = models.PositiveIntegerField(default=0)

    class Meta:
        ordering = ('position', )

    def __unicode__(self):
        return u'%s' % (self.title, )

<|edits_diff|>
--- customforms/models.py
+++ customforms/models.py
@@ -1,6 +1,7 @@
 #!/usr/bin/python
 # -*- coding: utf-8 -*-

+from django.core.urlresolvers import reverse
 from django.utils.translation import ugettext as _
 from django.db import models

@@ -14,6 +15,8 @@
     class Meta:
         ordering = ('title', )

+    def get_absolute_url(self):
+        return reverse('customforms.views.view_form', args=[str(self.id)])

 class Question(models.Model):
     form = models.ForeignKey(Form)
<|current_version|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from django.core.urlresolvers import reverse
from django.utils.translation import ugettext as _
from django.db import models

class Form(models.Model):
    title = models.CharField(_("Title"), max_length=255)

    def __unicode__(self):
        return u'%s' % self.title

    class Meta:
        ordering = ('title', )

    def get_absolute_url(self):
        return reverse('customforms.views.view_form', args=[str(self.id)])

class Question(models.Model):
    form = models.ForeignKey(Form)
    title = models.CharField(
        _("Title"), max_length=255, default=_("Question Title"))
    help_text = models.TextField(blank=True, null=True)
    CHOICES = [
        ('C', _('Checkbox')),
        ('R', _('Radio')),
        ('S', _('Select')),
        ('T', _('Text')),
        ]
    question_type = models.CharField(
        max_length=1, choices=CHOICES, default="T")
    required = models.BooleanField(default=False)
    position = models.PositiveIntegerField(default=0)

    def __unicode__(self):
        return u'%s' % (self.title, )

    class Meta:
        ordering = ('form', 'position', )

class Choice(models.Model):
    question = models.ForeignKey(Question)
    title = models.CharField(max_length=200,)
    position = models.PositiveIntegerField(default=0)

    class Meta:
        ordering = ('position', )

    def __unicode__(self):
        return u'%s' % (self.title, )

<|next_version|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from django.core.urlresolvers import reverse
from django.utils.translation import ugettext as _
from django.db import models

class Form(models.Model):
    title = models.CharField(_("Title"), max_length=255)

    def __unicode__(self):
        return u'%s' % self.title

    class Meta:
        ordering = ('title', )

    def get_absolute_url(self):
        return reverse('customforms.views.view_form', args=[str(self.id)])

class Question(models.Model):
    form = models.ForeignKey(Form)
    title = models.CharField(
        _("Title"), max_length=255, default=_("Question Title"))
    help_text = models.TextField(blank=True, null=True)
    CHOICES = [
        ('C', _('Checkbox')),
        ('R', _('Radio')),
        ('S', _('Select')),
        ('T', _('Text')),
        ]
    question_type = models.CharField(
        max_length=1, choices=CHOICES, default="T")
    required = models.BooleanField(default=False)
    position = models.PositiveIntegerField(default=0)

    def __unicode__(self):
        return u'%s' % (self.title, )

    class Meta:
        ordering = ('form', 'position', )

    def get_absolute_url(self):
        return reverse('customforms.views.view_form', args=[str(self.form.id)])

class Choice(models.Model):
    question = models.ForeignKey(Question)
    title = models.CharField(max_length=200,)
    position = models.PositiveIntegerField(default=0)

    class Meta:
        ordering = ('position', )

    def __unicode__(self):
        return u'%s' % (self.title, )


Add created and modified fields to Receipt

--- books/models.py
+++ books/models.py
@@ -1,11 +1,14 @@
 from django.contrib.auth.models import User
 from django.db import models
 from django.db.models import fields
+from django.utils import timezone

 class Receipt(models.Model):
     title = fields.CharField(max_length=255)
     price = fields.DecimalField(max_digits=10, decimal_places=2)
+    created = fields.DateTimeField(auto_now=True)
+    modified = fields.DateTimeField(default=timezone.now())
     user = models.ForeignKey(User)

     def __str__(self):

<|original_code|>
from django.contrib.auth.models import User
from django.db import models
from django.db.models import fields

class Receipt(models.Model):
    title = fields.CharField(max_length=255)
    price = fields.DecimalField(max_digits=10, decimal_places=2)
    user = models.ForeignKey(User)

    def __str__(self):
        return "{}_{}".format(self.title, self.price)

<|edits_diff|>
--- books/models.py
+++ books/models.py
@@ -1,6 +1,7 @@
 from django.contrib.auth.models import User
 from django.db import models
 from django.db.models import fields
+from django.utils import timezone

 class Receipt(models.Model):
<|current_version|>
from django.contrib.auth.models import User
from django.db import models
from django.db.models import fields
from django.utils import timezone

class Receipt(models.Model):
    title = fields.CharField(max_length=255)
    price = fields.DecimalField(max_digits=10, decimal_places=2)
    user = models.ForeignKey(User)

    def __str__(self):
        return "{}_{}".format(self.title, self.price)

<|next_version|>
from django.contrib.auth.models import User
from django.db import models
from django.db.models import fields
from django.utils import timezone

class Receipt(models.Model):
    title = fields.CharField(max_length=255)
    price = fields.DecimalField(max_digits=10, decimal_places=2)
    created = fields.DateTimeField(auto_now=True)
    modified = fields.DateTimeField(default=timezone.now())
    user = models.ForeignKey(User)

    def __str__(self):
        return "{}_{}".format(self.title, self.price)


Use current user as email author

Use current user as email author

--- mailer.py
+++ mailer.py
@@ -2,11 +2,15 @@
 from message import Message

 import sys
+import os
+import pwd
+import socket

 class Mailer:

   MAILER = MarrowMailer(dict(manager=dict(use='immediate'), transport=dict(use='sendmail')))
+  DEFAULT_AUTHOR = pwd.getpwuid(os.getuid()).pw_name + '@' + socket.getfqdn()

   @staticmethod
   def send(message):
@@ -25,6 +29,7 @@
     Mailer.start()

     message = Message(
+        author=Mailer.DEFAULT_AUTHOR,
         to=to_addr,
         subject='New transactions',
         plain=repr(transactions)

<|original_code|>
from marrow.mailer import Mailer as MarrowMailer
from message import Message

import sys

class Mailer:

  MAILER = MarrowMailer(dict(manager=dict(use='immediate'), transport=dict(use='sendmail')))

  @staticmethod
  def send(message):
    Mailer.MAILER.send(message)

  @staticmethod
  def start():
    Mailer.MAILER.start()

  @staticmethod
  def stop():
    Mailer.MAILER.stop()

  @staticmethod
  def send_transactions(transactions, to_addr):
    Mailer.start()

    message = Message(
        to=to_addr,
        subject='New transactions',
        plain=repr(transactions)
    )
    Mailer.send(message)

    Mailer.stop()

  @staticmethod
  def get_cli_email_addr():
    try:
      return sys.argv[1]
    except IndexError:
      return None

<|edits_diff|>
--- mailer.py
+++ mailer.py
@@ -2,11 +2,15 @@
 from message import Message

 import sys
+import os
+import pwd
+import socket

 class Mailer:

   MAILER = MarrowMailer(dict(manager=dict(use='immediate'), transport=dict(use='sendmail')))
+  DEFAULT_AUTHOR = pwd.getpwuid(os.getuid()).pw_name + '@' + socket.getfqdn()

   @staticmethod
   def send(message):
<|current_version|>
from marrow.mailer import Mailer as MarrowMailer
from message import Message

import sys
import os
import pwd
import socket

class Mailer:

  MAILER = MarrowMailer(dict(manager=dict(use='immediate'), transport=dict(use='sendmail')))
  DEFAULT_AUTHOR = pwd.getpwuid(os.getuid()).pw_name + '@' + socket.getfqdn()

  @staticmethod
  def send(message):
    Mailer.MAILER.send(message)

  @staticmethod
  def start():
    Mailer.MAILER.start()

  @staticmethod
  def stop():
    Mailer.MAILER.stop()

  @staticmethod
  def send_transactions(transactions, to_addr):
    Mailer.start()

    message = Message(
        to=to_addr,
        subject='New transactions',
        plain=repr(transactions)
    )
    Mailer.send(message)

    Mailer.stop()

  @staticmethod
  def get_cli_email_addr():
    try:
      return sys.argv[1]
    except IndexError:
      return None

<|next_version|>
from marrow.mailer import Mailer as MarrowMailer
from message import Message

import sys
import os
import pwd
import socket

class Mailer:

  MAILER = MarrowMailer(dict(manager=dict(use='immediate'), transport=dict(use='sendmail')))
  DEFAULT_AUTHOR = pwd.getpwuid(os.getuid()).pw_name + '@' + socket.getfqdn()

  @staticmethod
  def send(message):
    Mailer.MAILER.send(message)

  @staticmethod
  def start():
    Mailer.MAILER.start()

  @staticmethod
  def stop():
    Mailer.MAILER.stop()

  @staticmethod
  def send_transactions(transactions, to_addr):
    Mailer.start()

    message = Message(
        author=Mailer.DEFAULT_AUTHOR,
        to=to_addr,
        subject='New transactions',
        plain=repr(transactions)
    )
    Mailer.send(message)

    Mailer.stop()

  @staticmethod
  def get_cli_email_addr():
    try:
      return sys.argv[1]
    except IndexError:
      return None


Handle logging unicode messages in python2.

Former-commit-id: 257d94eb71d5597ff52a18ec1530d73496901ef4

--- scripts/utils.py
+++ scripts/utils.py
@@ -19,6 +19,7 @@
         self._mode = 'INFO'

     def progress(self, message):
+        message = e(message)
         if not sys.stderr.isatty():
             return

@@ -28,6 +29,7 @@
         self._mode = 'PROGRESS'

     def info(self, message):
+        message = e(message)
         if self._mode == 'PROGRESS':
             print >>sys.stderr

<|original_code|>
import sys
import hashlib

def e(s):
    if type(s) == str:
        return str
    return s.encode('utf-8')

def d(s):
    if type(s) == unicode:
        return s
    return unicode(s, 'utf-8')

def mkid(s):
    return hashlib.sha1(e(s)).hexdigest()[:2*4]

class Logger(object):
    def __init__(self):
        self._mode = 'INFO'

    def progress(self, message):
        if not sys.stderr.isatty():
            return

        if self._mode == 'PROGRESS':
            print >>sys.stderr, '\r',
        print >>sys.stderr, message,
        self._mode = 'PROGRESS'

    def info(self, message):
        if self._mode == 'PROGRESS':
            print >>sys.stderr

        print >>sys.stderr, message
        self._mode = 'INFO'

<|edits_diff|>
--- scripts/utils.py
+++ scripts/utils.py
@@ -19,6 +19,7 @@
         self._mode = 'INFO'

     def progress(self, message):
+        message = e(message)
         if not sys.stderr.isatty():
             return

<|current_version|>
import sys
import hashlib

def e(s):
    if type(s) == str:
        return str
    return s.encode('utf-8')

def d(s):
    if type(s) == unicode:
        return s
    return unicode(s, 'utf-8')

def mkid(s):
    return hashlib.sha1(e(s)).hexdigest()[:2*4]

class Logger(object):
    def __init__(self):
        self._mode = 'INFO'

    def progress(self, message):
        message = e(message)
        if not sys.stderr.isatty():
            return

        if self._mode == 'PROGRESS':
            print >>sys.stderr, '\r',
        print >>sys.stderr, message,
        self._mode = 'PROGRESS'

    def info(self, message):
        if self._mode == 'PROGRESS':
            print >>sys.stderr

        print >>sys.stderr, message
        self._mode = 'INFO'

<|next_version|>
import sys
import hashlib

def e(s):
    if type(s) == str:
        return str
    return s.encode('utf-8')

def d(s):
    if type(s) == unicode:
        return s
    return unicode(s, 'utf-8')

def mkid(s):
    return hashlib.sha1(e(s)).hexdigest()[:2*4]

class Logger(object):
    def __init__(self):
        self._mode = 'INFO'

    def progress(self, message):
        message = e(message)
        if not sys.stderr.isatty():
            return

        if self._mode == 'PROGRESS':
            print >>sys.stderr, '\r',
        print >>sys.stderr, message,
        self._mode = 'PROGRESS'

    def info(self, message):
        message = e(message)
        if self._mode == 'PROGRESS':
            print >>sys.stderr

        print >>sys.stderr, message
        self._mode = 'INFO'


Remove updated at while comparing.

Remove updated at while comparing.

--- system/t04_mirror/show.py
+++ system/t04_mirror/show.py
@@ -1,4 +1,5 @@
 from lib import BaseTest
+import re

 class ShowMirror1Test(BaseTest):
@@ -23,3 +24,4 @@
     """
     fixtureDB = True
     runCmd = "aptly mirror show --with-packages wheezy-contrib"
+    outputMatchPrepare = lambda _, s: re.sub(r"Last update: [0-9:A-Za-z -]+\n", "", s)

<|original_code|>
from lib import BaseTest

class ShowMirror1Test(BaseTest):
    """
    show mirror: regular mirror
    """
    fixtureCmds = ["aptly mirror create mirror1 http://mirror.yandex.ru/debian/ wheezy"]
    runCmd = "aptly mirror show mirror1"

class ShowMirror2Test(BaseTest):
    """
    show mirror: missing mirror
    """
    runCmd = "aptly mirror show mirror-xx"
    expectedCode = 1

class ShowMirror3Test(BaseTest):
    """
    show mirror: regular mirror with packages
    """
    fixtureDB = True
    runCmd = "aptly mirror show --with-packages wheezy-contrib"

<|edits_diff|>
--- system/t04_mirror/show.py
+++ system/t04_mirror/show.py
@@ -1,4 +1,5 @@
 from lib import BaseTest
+import re

 class ShowMirror1Test(BaseTest):
<|current_version|>
from lib import BaseTest
import re

class ShowMirror1Test(BaseTest):
    """
    show mirror: regular mirror
    """
    fixtureCmds = ["aptly mirror create mirror1 http://mirror.yandex.ru/debian/ wheezy"]
    runCmd = "aptly mirror show mirror1"

class ShowMirror2Test(BaseTest):
    """
    show mirror: missing mirror
    """
    runCmd = "aptly mirror show mirror-xx"
    expectedCode = 1

class ShowMirror3Test(BaseTest):
    """
    show mirror: regular mirror with packages
    """
    fixtureDB = True
    runCmd = "aptly mirror show --with-packages wheezy-contrib"

<|next_version|>
from lib import BaseTest
import re

class ShowMirror1Test(BaseTest):
    """
    show mirror: regular mirror
    """
    fixtureCmds = ["aptly mirror create mirror1 http://mirror.yandex.ru/debian/ wheezy"]
    runCmd = "aptly mirror show mirror1"

class ShowMirror2Test(BaseTest):
    """
    show mirror: missing mirror
    """
    runCmd = "aptly mirror show mirror-xx"
    expectedCode = 1

class ShowMirror3Test(BaseTest):
    """
    show mirror: regular mirror with packages
    """
    fixtureDB = True
    runCmd = "aptly mirror show --with-packages wheezy-contrib"
    outputMatchPrepare = lambda _, s: re.sub(r"Last update: [0-9:A-Za-z -]+\n", "", s)


Add docstrings to Automaton base class

Add docstrings to Automaton base class

--- automata/automaton.py
+++ automata/automaton.py
@@ -4,6 +4,7 @@

 class Automaton(metaclass=abc.ABCMeta):
+    """an abstract base class for finite automata"""

     def __init__(self, states, symbols, transitions, initial_state,
                  final_states):
@@ -17,10 +18,14 @@

     @abc.abstractmethod
     def validate_input(self):
+        """returns True if the given string is accepted by this automaton;
+        raises the appropriate exception if the string is not accepted"""
         pass

     @abc.abstractmethod
     def validate_automaton(self):
+        """returns True if this automaton is internally consistent;
+        raises the appropriate exception if this automaton is invalid"""
         pass

<|original_code|>
#!/usr/bin/env python3

import abc

class Automaton(metaclass=abc.ABCMeta):

    def __init__(self, states, symbols, transitions, initial_state,
                 final_states):
        """initialize a complete finite automaton"""
        self.states = states
        self.symbols = symbols
        self.transitions = transitions
        self.initial_state = initial_state
        self.final_states = final_states
        self.validate_automaton()

    @abc.abstractmethod
    def validate_input(self):
        pass

    @abc.abstractmethod
    def validate_automaton(self):
        pass

class AutomatonError(Exception):
    """the base class for all automaton-related errors"""
    pass

class InvalidStateError(AutomatonError):
    """a state is not a valid state for this automaton"""
    pass

class InvalidSymbolError(AutomatonError):
    """a symbol is not a valid symbol for this automaton"""
    pass

class MissingStateError(AutomatonError):
    """a state is missing from the transition function"""
    pass

class MissingSymbolError(AutomatonError):
    """a symbol is missing from the transition function"""
    pass

class FinalStateError(AutomatonError):
    """the automaton stopped at a non-final state"""
    pass

<|edits_diff|>
--- automata/automaton.py
+++ automata/automaton.py
@@ -4,6 +4,7 @@

 class Automaton(metaclass=abc.ABCMeta):
+    """an abstract base class for finite automata"""

     def __init__(self, states, symbols, transitions, initial_state,
                  final_states):
@@ -17,6 +18,8 @@

     @abc.abstractmethod
     def validate_input(self):
+        """returns True if the given string is accepted by this automaton;
+        raises the appropriate exception if the string is not accepted"""
         pass

     @abc.abstractmethod
<|current_version|>
#!/usr/bin/env python3

import abc

class Automaton(metaclass=abc.ABCMeta):
    """an abstract base class for finite automata"""

    def __init__(self, states, symbols, transitions, initial_state,
                 final_states):
        """initialize a complete finite automaton"""
        self.states = states
        self.symbols = symbols
        self.transitions = transitions
        self.initial_state = initial_state
        self.final_states = final_states
        self.validate_automaton()

    @abc.abstractmethod
    def validate_input(self):
        """returns True if the given string is accepted by this automaton;
        raises the appropriate exception if the string is not accepted"""
        pass

    @abc.abstractmethod
    def validate_automaton(self):
        pass

class AutomatonError(Exception):
    """the base class for all automaton-related errors"""
    pass

class InvalidStateError(AutomatonError):
    """a state is not a valid state for this automaton"""
    pass

class InvalidSymbolError(AutomatonError):
    """a symbol is not a valid symbol for this automaton"""
    pass

class MissingStateError(AutomatonError):
    """a state is missing from the transition function"""
    pass

class MissingSymbolError(AutomatonError):
    """a symbol is missing from the transition function"""
    pass

class FinalStateError(AutomatonError):
    """the automaton stopped at a non-final state"""
    pass

<|next_version|>
#!/usr/bin/env python3

import abc

class Automaton(metaclass=abc.ABCMeta):
    """an abstract base class for finite automata"""

    def __init__(self, states, symbols, transitions, initial_state,
                 final_states):
        """initialize a complete finite automaton"""
        self.states = states
        self.symbols = symbols
        self.transitions = transitions
        self.initial_state = initial_state
        self.final_states = final_states
        self.validate_automaton()

    @abc.abstractmethod
    def validate_input(self):
        """returns True if the given string is accepted by this automaton;
        raises the appropriate exception if the string is not accepted"""
        pass

    @abc.abstractmethod
    def validate_automaton(self):
        """returns True if this automaton is internally consistent;
        raises the appropriate exception if this automaton is invalid"""
        pass

class AutomatonError(Exception):
    """the base class for all automaton-related errors"""
    pass

class InvalidStateError(AutomatonError):
    """a state is not a valid state for this automaton"""
    pass

class InvalidSymbolError(AutomatonError):
    """a symbol is not a valid symbol for this automaton"""
    pass

class MissingStateError(AutomatonError):
    """a state is missing from the transition function"""
    pass

class MissingSymbolError(AutomatonError):
    """a symbol is missing from the transition function"""
    pass

class FinalStateError(AutomatonError):
    """the automaton stopped at a non-final state"""
    pass


Make command-keyword compatible with DFW implementation

--- Cauldron/ext/commandkeywords/__init__.py
+++ Cauldron/ext/commandkeywords/__init__.py
@@ -6,6 +6,7 @@

 from Cauldron.types import Boolean, DispatcherKeywordType
 from Cauldron.exc import NoWriteNecessary
+from Cauldron.utils.callbacks import Callbacks

 class CommandKeyword(Boolean, DispatcherKeywordType):
     """This keyword will receive boolean writes as 1, and will always be set to 0.
@@ -20,6 +21,11 @@
     def __init__(self, *args, **kwargs):
         kwargs['initial'] = '0'
         super(CommandKeyword, self).__init__(*args, **kwargs)
+        self._cbs = Callbacks()
+
+    def command(self, func):
+        """Add command items."""
+        self._cbs.add(func)

     def prewrite(self, value):
         """Before writing, trigger no-write-necssary if value is False"""
@@ -27,6 +33,11 @@
             raise NoWriteNecessary("No write needed, command not triggered.")
         return super(CommandKeyword, self).prewrite(value)

+    def write(self, value):
+        """Write to the commands."""
+        if str(value) == '1':
+            self._cbs(self)
+
     def postwrite(self, value):
         """Special postwrite that always sets the value to '0'."""
         self.set('0', force=True)

<|original_code|>
# -*- coding: utf-8 -*-
"""
An extension for a command-based keyword.
"""
from __future__ import absolute_import

from Cauldron.types import Boolean, DispatcherKeywordType
from Cauldron.exc import NoWriteNecessary

class CommandKeyword(Boolean, DispatcherKeywordType):
    """This keyword will receive boolean writes as 1, and will always be set to 0.

        Actions can then be performed in callbacks, etc., every time this keyword is triggered.
    """

    KTL_REGISTERED = False

    KTL_TYPE = 'boolean'

    def __init__(self, *args, **kwargs):
        kwargs['initial'] = '0'
        super(CommandKeyword, self).__init__(*args, **kwargs)

    def prewrite(self, value):
        """Before writing, trigger no-write-necssary if value is False"""
        if self.translate(value) == '0':
            raise NoWriteNecessary("No write needed, command not triggered.")
        return super(CommandKeyword, self).prewrite(value)

    def postwrite(self, value):
        """Special postwrite that always sets the value to '0'."""
        self.set('0', force=True)

    # We don't have to do anything else here.

<|edits_diff|>
--- Cauldron/ext/commandkeywords/__init__.py
+++ Cauldron/ext/commandkeywords/__init__.py
@@ -6,6 +6,7 @@

 from Cauldron.types import Boolean, DispatcherKeywordType
 from Cauldron.exc import NoWriteNecessary
+from Cauldron.utils.callbacks import Callbacks

 class CommandKeyword(Boolean, DispatcherKeywordType):
     """This keyword will receive boolean writes as 1, and will always be set to 0.
@@ -20,6 +21,11 @@
     def __init__(self, *args, **kwargs):
         kwargs['initial'] = '0'
         super(CommandKeyword, self).__init__(*args, **kwargs)
+        self._cbs = Callbacks()
+
+    def command(self, func):
+        """Add command items."""
+        self._cbs.add(func)

     def prewrite(self, value):
         """Before writing, trigger no-write-necssary if value is False"""
<|current_version|>
# -*- coding: utf-8 -*-
"""
An extension for a command-based keyword.
"""
from __future__ import absolute_import

from Cauldron.types import Boolean, DispatcherKeywordType
from Cauldron.exc import NoWriteNecessary
from Cauldron.utils.callbacks import Callbacks

class CommandKeyword(Boolean, DispatcherKeywordType):
    """This keyword will receive boolean writes as 1, and will always be set to 0.

        Actions can then be performed in callbacks, etc., every time this keyword is triggered.
    """

    KTL_REGISTERED = False

    KTL_TYPE = 'boolean'

    def __init__(self, *args, **kwargs):
        kwargs['initial'] = '0'
        super(CommandKeyword, self).__init__(*args, **kwargs)
        self._cbs = Callbacks()

    def command(self, func):
        """Add command items."""
        self._cbs.add(func)

    def prewrite(self, value):
        """Before writing, trigger no-write-necssary if value is False"""
        if self.translate(value) == '0':
            raise NoWriteNecessary("No write needed, command not triggered.")
        return super(CommandKeyword, self).prewrite(value)

    def postwrite(self, value):
        """Special postwrite that always sets the value to '0'."""
        self.set('0', force=True)

    # We don't have to do anything else here.

<|next_version|>
# -*- coding: utf-8 -*-
"""
An extension for a command-based keyword.
"""
from __future__ import absolute_import

from Cauldron.types import Boolean, DispatcherKeywordType
from Cauldron.exc import NoWriteNecessary
from Cauldron.utils.callbacks import Callbacks

class CommandKeyword(Boolean, DispatcherKeywordType):
    """This keyword will receive boolean writes as 1, and will always be set to 0.

        Actions can then be performed in callbacks, etc., every time this keyword is triggered.
    """

    KTL_REGISTERED = False

    KTL_TYPE = 'boolean'

    def __init__(self, *args, **kwargs):
        kwargs['initial'] = '0'
        super(CommandKeyword, self).__init__(*args, **kwargs)
        self._cbs = Callbacks()

    def command(self, func):
        """Add command items."""
        self._cbs.add(func)

    def prewrite(self, value):
        """Before writing, trigger no-write-necssary if value is False"""
        if self.translate(value) == '0':
            raise NoWriteNecessary("No write needed, command not triggered.")
        return super(CommandKeyword, self).prewrite(value)

    def write(self, value):
        """Write to the commands."""
        if str(value) == '1':
            self._cbs(self)

    def postwrite(self, value):
        """Special postwrite that always sets the value to '0'."""
        self.set('0', force=True)

    # We don't have to do anything else here.


Increase loglevel during test execution

Increase loglevel during test execution

--- test/conftest.py
+++ test/conftest.py
@@ -12,8 +12,12 @@
 # either express or implied. See the License for the specific
 # language governing permissions and limitations under the License.

+import logging
+
 from sqlalchemy import event, Column, Sequence
 from sqlalchemy.dialects import registry
+
+logging.getLogger('sqlalchemy.engine').setLevel(logging.DEBUG)

 registry.register("hana", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
 registry.register("hana.hdbcli", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")

<|original_code|>
# Copyright 2015 SAP SE.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http: //www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the License.

from sqlalchemy import event, Column, Sequence
from sqlalchemy.dialects import registry

registry.register("hana", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.hdbcli", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.pyhdb", "sqlalchemy_hana.dialect", "HANAPyHDBDialect")

@event.listens_for(Column, "after_parent_attach")
def add_test_seq(column, table):
    if column.info.get('test_needs_autoincrement', False):
        column._init_items(
            Sequence(table.name + '_' + column.name + '_seq')
        )

from sqlalchemy.testing.plugin.pytestplugin import *

<|edits_diff|>
--- test/conftest.py
+++ test/conftest.py
@@ -11,6 +11,8 @@
 # "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
 # either express or implied. See the License for the specific
 # language governing permissions and limitations under the License.
+
+import logging

 from sqlalchemy import event, Column, Sequence
 from sqlalchemy.dialects import registry
<|current_version|>
# Copyright 2015 SAP SE.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http: //www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the License.

import logging

from sqlalchemy import event, Column, Sequence
from sqlalchemy.dialects import registry

registry.register("hana", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.hdbcli", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.pyhdb", "sqlalchemy_hana.dialect", "HANAPyHDBDialect")

@event.listens_for(Column, "after_parent_attach")
def add_test_seq(column, table):
    if column.info.get('test_needs_autoincrement', False):
        column._init_items(
            Sequence(table.name + '_' + column.name + '_seq')
        )

from sqlalchemy.testing.plugin.pytestplugin import *

<|next_version|>
# Copyright 2015 SAP SE.
#
# Licensed under the Apache License, Version 2.0 (the "License");
# you may not use this file except in compliance with the License.
# You may obtain a copy of the License at
#
# http: //www.apache.org/licenses/LICENSE-2.0
#
# Unless required by applicable law or agreed to in writing,
# software distributed under the License is distributed on an
# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND,
# either express or implied. See the License for the specific
# language governing permissions and limitations under the License.

import logging

from sqlalchemy import event, Column, Sequence
from sqlalchemy.dialects import registry

logging.getLogger('sqlalchemy.engine').setLevel(logging.DEBUG)

registry.register("hana", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.hdbcli", "sqlalchemy_hana.dialect", "HANAHDBCLIDialect")
registry.register("hana.pyhdb", "sqlalchemy_hana.dialect", "HANAPyHDBDialect")

@event.listens_for(Column, "after_parent_attach")
def add_test_seq(column, table):
    if column.info.get('test_needs_autoincrement', False):
        column._init_items(
            Sequence(table.name + '_' + column.name + '_seq')
        )

from sqlalchemy.testing.plugin.pytestplugin import *


Set Meta class model default on ContainerAdminForm

--- opps/containers/forms.py
+++ opps/containers/forms.py
@@ -6,6 +6,8 @@
 from opps.db.models.fields.jsonf import JSONFormField
 from opps.fields.widgets import JSONField
 from opps.fields.models import Field, FieldOption
+
+from .models import Container

 class ContainerAdminForm(forms.ModelForm):
@@ -31,3 +33,6 @@
                 self.fields[
                     'json_{}'.format(field.slug)
                 ] = forms.CharField(required=False)
+
+    class Meta:
+        model = Container

<|original_code|>
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from django import forms
from django.conf import settings

from opps.db.models.fields.jsonf import JSONFormField
from opps.fields.widgets import JSONField
from opps.fields.models import Field, FieldOption

class ContainerAdminForm(forms.ModelForm):
    def __init__(self, *args, **kwargs):
        super(ContainerAdminForm, self).__init__(*args, **kwargs)

        if not settings.OPPS_MIRROR_CHANNEL:
            self.fields['mirror_channel'].widget = forms.HiddenInput()

        self.fields['json'] = JSONFormField(
            widget=JSONField(
                attrs={'_model': self._meta.model.__name__}),
            required=False)
        for field in Field.objects.filter(application__contains=
                                          self._meta.model.__name__):
            if field.type == 'checkbox':
                for fo in FieldOption.objects.filter(field=field):
                    self.fields[
                        'json_{}_{}'.format(
                            field.slug, fo.option.slug
                        )] = forms.CharField(required=False)
            else:
                self.fields[
                    'json_{}'.format(field.slug)
                ] = forms.CharField(required=False)

<|edits_diff|>
--- opps/containers/forms.py
+++ opps/containers/forms.py
@@ -6,6 +6,8 @@
 from opps.db.models.fields.jsonf import JSONFormField
 from opps.fields.widgets import JSONField
 from opps.fields.models import Field, FieldOption
+
+from .models import Container

 class ContainerAdminForm(forms.ModelForm):
<|current_version|>
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from django import forms
from django.conf import settings

from opps.db.models.fields.jsonf import JSONFormField
from opps.fields.widgets import JSONField
from opps.fields.models import Field, FieldOption

from .models import Container

class ContainerAdminForm(forms.ModelForm):
    def __init__(self, *args, **kwargs):
        super(ContainerAdminForm, self).__init__(*args, **kwargs)

        if not settings.OPPS_MIRROR_CHANNEL:
            self.fields['mirror_channel'].widget = forms.HiddenInput()

        self.fields['json'] = JSONFormField(
            widget=JSONField(
                attrs={'_model': self._meta.model.__name__}),
            required=False)
        for field in Field.objects.filter(application__contains=
                                          self._meta.model.__name__):
            if field.type == 'checkbox':
                for fo in FieldOption.objects.filter(field=field):
                    self.fields[
                        'json_{}_{}'.format(
                            field.slug, fo.option.slug
                        )] = forms.CharField(required=False)
            else:
                self.fields[
                    'json_{}'.format(field.slug)
                ] = forms.CharField(required=False)

<|next_version|>
#!/usr/bin/env python
# -*- coding: utf-8 -*-
from django import forms
from django.conf import settings

from opps.db.models.fields.jsonf import JSONFormField
from opps.fields.widgets import JSONField
from opps.fields.models import Field, FieldOption

from .models import Container

class ContainerAdminForm(forms.ModelForm):
    def __init__(self, *args, **kwargs):
        super(ContainerAdminForm, self).__init__(*args, **kwargs)

        if not settings.OPPS_MIRROR_CHANNEL:
            self.fields['mirror_channel'].widget = forms.HiddenInput()

        self.fields['json'] = JSONFormField(
            widget=JSONField(
                attrs={'_model': self._meta.model.__name__}),
            required=False)
        for field in Field.objects.filter(application__contains=
                                          self._meta.model.__name__):
            if field.type == 'checkbox':
                for fo in FieldOption.objects.filter(field=field):
                    self.fields[
                        'json_{}_{}'.format(
                            field.slug, fo.option.slug
                        )] = forms.CharField(required=False)
            else:
                self.fields[
                    'json_{}'.format(field.slug)
                ] = forms.CharField(required=False)

    class Meta:
        model = Container


ADD description / contact / daa fields

ADD description / contact / daa fields

--- packages/syft/src/syft/core/node/common/node_table/setup.py
+++ packages/syft/src/syft/core/node/common/node_table/setup.py
@@ -2,6 +2,7 @@
 from sqlalchemy import Column
 from sqlalchemy import Integer
 from sqlalchemy import String
+from sqlalchemy import Boolean

 # relative
 from . import Base
@@ -12,6 +13,9 @@

     id = Column(Integer(), primary_key=True, autoincrement=True)
     domain_name = Column(String(255), default="")
+    description = Column(String(255), default="")
+    contact = Column(String(255), default="")
+    daa = Column(Boolean(), default=False)
     node_id = Column(String(32), default="")

     def __str__(self) -> str:

<|original_code|>
# third party
from sqlalchemy import Column
from sqlalchemy import Integer
from sqlalchemy import String

# relative
from . import Base

class SetupConfig(Base):
    __tablename__ = "setup"

    id = Column(Integer(), primary_key=True, autoincrement=True)
    domain_name = Column(String(255), default="")
    node_id = Column(String(32), default="")

    def __str__(self) -> str:
        return f"<Domain Name: {self.domain_name}>"

def create_setup(id: int, domain_name: str, node_id: str) -> SetupConfig:
    return SetupConfig(id=id, domain_name=domain_name, node_id=node_id)

<|edits_diff|>
--- packages/syft/src/syft/core/node/common/node_table/setup.py
+++ packages/syft/src/syft/core/node/common/node_table/setup.py
@@ -2,6 +2,7 @@
 from sqlalchemy import Column
 from sqlalchemy import Integer
 from sqlalchemy import String
+from sqlalchemy import Boolean

 # relative
 from . import Base
<|current_version|>
# third party
from sqlalchemy import Column
from sqlalchemy import Integer
from sqlalchemy import String
from sqlalchemy import Boolean

# relative
from . import Base

class SetupConfig(Base):
    __tablename__ = "setup"

    id = Column(Integer(), primary_key=True, autoincrement=True)
    domain_name = Column(String(255), default="")
    node_id = Column(String(32), default="")

    def __str__(self) -> str:
        return f"<Domain Name: {self.domain_name}>"

def create_setup(id: int, domain_name: str, node_id: str) -> SetupConfig:
    return SetupConfig(id=id, domain_name=domain_name, node_id=node_id)

<|next_version|>
# third party
from sqlalchemy import Column
from sqlalchemy import Integer
from sqlalchemy import String
from sqlalchemy import Boolean

# relative
from . import Base

class SetupConfig(Base):
    __tablename__ = "setup"

    id = Column(Integer(), primary_key=True, autoincrement=True)
    domain_name = Column(String(255), default="")
    description = Column(String(255), default="")
    contact = Column(String(255), default="")
    daa = Column(Boolean(), default=False)
    node_id = Column(String(32), default="")

    def __str__(self) -> str:
        return f"<Domain Name: {self.domain_name}>"

def create_setup(id: int, domain_name: str, node_id: str) -> SetupConfig:
    return SetupConfig(id=id, domain_name=domain_name, node_id=node_id)


Fix race condition during `mimetypes` initialization.

Initial patch from Steven R. Loomis.
Closes #8629.

--- trac/web/__init__.py
+++ trac/web/__init__.py
@@ -1,8 +1,14 @@
+# Workaround for http://bugs.python.org/issue6763 and
+# http://bugs.python.org/issue5853 thread issues
+import mimetypes
+mimetypes.init()
+
 # With mod_python we'll have to delay importing trac.web.api until
 # modpython_frontend.handler() has been called since the
 # PYTHON_EGG_CACHE variable is set from there
 #
 # TODO: Remove this once the Genshi zip_safe issue has been resolved.
+
 import os
 from pkg_resources import get_distribution
 if not os.path.isdir(get_distribution('genshi').location):

<|original_code|>
# With mod_python we'll have to delay importing trac.web.api until
# modpython_frontend.handler() has been called since the
# PYTHON_EGG_CACHE variable is set from there
#
# TODO: Remove this once the Genshi zip_safe issue has been resolved.
import os
from pkg_resources import get_distribution
if not os.path.isdir(get_distribution('genshi').location):
    try:
        import mod_python.apache
        import sys
        if 'trac.web.modpython_frontend' in sys.modules:
            from trac.web.api import *
    except ImportError:
        from trac.web.api import *
else:
    from trac.web.api import *

<|edits_diff|>
--- trac/web/__init__.py
+++ trac/web/__init__.py
@@ -1,3 +1,8 @@
+# Workaround for http://bugs.python.org/issue6763 and
+# http://bugs.python.org/issue5853 thread issues
+import mimetypes
+mimetypes.init()
+
 # With mod_python we'll have to delay importing trac.web.api until
 # modpython_frontend.handler() has been called since the
 # PYTHON_EGG_CACHE variable is set from there
<|current_version|>
# Workaround for http://bugs.python.org/issue6763 and
# http://bugs.python.org/issue5853 thread issues
import mimetypes
mimetypes.init()

# With mod_python we'll have to delay importing trac.web.api until
# modpython_frontend.handler() has been called since the
# PYTHON_EGG_CACHE variable is set from there
#
# TODO: Remove this once the Genshi zip_safe issue has been resolved.
import os
from pkg_resources import get_distribution
if not os.path.isdir(get_distribution('genshi').location):
    try:
        import mod_python.apache
        import sys
        if 'trac.web.modpython_frontend' in sys.modules:
            from trac.web.api import *
    except ImportError:
        from trac.web.api import *
else:
    from trac.web.api import *

<|next_version|>
# Workaround for http://bugs.python.org/issue6763 and
# http://bugs.python.org/issue5853 thread issues
import mimetypes
mimetypes.init()

# With mod_python we'll have to delay importing trac.web.api until
# modpython_frontend.handler() has been called since the
# PYTHON_EGG_CACHE variable is set from there
#
# TODO: Remove this once the Genshi zip_safe issue has been resolved.

import os
from pkg_resources import get_distribution
if not os.path.isdir(get_distribution('genshi').location):
    try:
        import mod_python.apache
        import sys
        if 'trac.web.modpython_frontend' in sys.modules:
            from trac.web.api import *
    except ImportError:
        from trac.web.api import *
else:
    from trac.web.api import *


Add way to remove old pastes

Add way to remove old pastes

--- manage.py
+++ manage.py
@@ -1,6 +1,8 @@
 __author__ = 'zifnab'
 from flask_script import Manager, Server
 from app import app
+from database import Paste
+import arrow

 manager=Manager(app)

@@ -10,6 +12,11 @@
 def print_routes():
     for rule in app.url_map.iter_rules():
         print rule
+@manager.command
+def remove_expired():
+    for paste in Paste.objects(expire__lt=arrow.now().datetime, user=None):
+        print 'delete {0}'.format(paste.name)
+        paste.delete()

 if __name__ == '__main__':
     manager.run()

<|original_code|>
__author__ = 'zifnab'
from flask_script import Manager, Server
from app import app

manager=Manager(app)

manager.add_command('runserver', Server(host=app.config.get('HOST', '0.0.0.0'), port=app.config.get('PORT', 5000)))

@manager.command
def print_routes():
    for rule in app.url_map.iter_rules():
        print rule

if __name__ == '__main__':
    manager.run()
<|edits_diff|>
--- manage.py
+++ manage.py
@@ -1,6 +1,8 @@
 __author__ = 'zifnab'
 from flask_script import Manager, Server
 from app import app
+from database import Paste
+import arrow

 manager=Manager(app)

<|current_version|>
__author__ = 'zifnab'
from flask_script import Manager, Server
from app import app
from database import Paste
import arrow

manager=Manager(app)

manager.add_command('runserver', Server(host=app.config.get('HOST', '0.0.0.0'), port=app.config.get('PORT', 5000)))

@manager.command
def print_routes():
    for rule in app.url_map.iter_rules():
        print rule

if __name__ == '__main__':
    manager.run()
<|next_version|>
__author__ = 'zifnab'
from flask_script import Manager, Server
from app import app
from database import Paste
import arrow

manager=Manager(app)

manager.add_command('runserver', Server(host=app.config.get('HOST', '0.0.0.0'), port=app.config.get('PORT', 5000)))

@manager.command
def print_routes():
    for rule in app.url_map.iter_rules():
        print rule
@manager.command
def remove_expired():
    for paste in Paste.objects(expire__lt=arrow.now().datetime, user=None):
        print 'delete {0}'.format(paste.name)
        paste.delete()

if __name__ == '__main__':
    manager.run()


Add a verbose error reporting on Travis

Add a verbose error reporting on Travis

--- unitTestUtils/parseXML.py
+++ unitTestUtils/parseXML.py
@@ -16,8 +16,10 @@
             tree = ET.parse(infile)
             root = tree.getroot()
             if root.findall('.//FatalError'):
+                element=root.findall('.//FatalError')[0]
                 eprint("Error detected")
                 print(infile)
+                print(element.text)
                 sys.exit(1)
         except ParseError:
             eprint("The file xml isn't correct. There were some mistakes in the tests ")

<|original_code|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from __future__ import print_function
from xml.etree.ElementTree import ParseError
import xml.etree.ElementTree as ET
import glob
import sys

def eprint(*args, **kwargs):
    print(*args, file=sys.stderr, **kwargs)

def parse():
    for infile in glob.glob('*.xml'):
        try:
            tree = ET.parse(infile)
            root = tree.getroot()
            if root.findall('.//FatalError'):
                eprint("Error detected")
                print(infile)
                sys.exit(1)
        except ParseError:
            eprint("The file xml isn't correct. There were some mistakes in the tests ")
            sys.exit(1)

def main():
    parse()

if __name__ == '__main__':
    main()

<|edits_diff|>
--- unitTestUtils/parseXML.py
+++ unitTestUtils/parseXML.py
@@ -16,6 +16,7 @@
             tree = ET.parse(infile)
             root = tree.getroot()
             if root.findall('.//FatalError'):
+                element=root.findall('.//FatalError')[0]
                 eprint("Error detected")
                 print(infile)
                 sys.exit(1)
<|current_version|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from __future__ import print_function
from xml.etree.ElementTree import ParseError
import xml.etree.ElementTree as ET
import glob
import sys

def eprint(*args, **kwargs):
    print(*args, file=sys.stderr, **kwargs)

def parse():
    for infile in glob.glob('*.xml'):
        try:
            tree = ET.parse(infile)
            root = tree.getroot()
            if root.findall('.//FatalError'):
                element=root.findall('.//FatalError')[0]
                eprint("Error detected")
                print(infile)
                sys.exit(1)
        except ParseError:
            eprint("The file xml isn't correct. There were some mistakes in the tests ")
            sys.exit(1)

def main():
    parse()

if __name__ == '__main__':
    main()

<|next_version|>
#!/usr/bin/python
# -*- coding: utf-8 -*-

from __future__ import print_function
from xml.etree.ElementTree import ParseError
import xml.etree.ElementTree as ET
import glob
import sys

def eprint(*args, **kwargs):
    print(*args, file=sys.stderr, **kwargs)

def parse():
    for infile in glob.glob('*.xml'):
        try:
            tree = ET.parse(infile)
            root = tree.getroot()
            if root.findall('.//FatalError'):
                element=root.findall('.//FatalError')[0]
                eprint("Error detected")
                print(infile)
                print(element.text)
                sys.exit(1)
        except ParseError:
            eprint("The file xml isn't correct. There were some mistakes in the tests ")
            sys.exit(1)

def main():
    parse()

if __name__ == '__main__':
    main()


Fix plugin permission data migration

Fix plugin permission data migration

--- saleor/account/migrations/0040_auto_20200415_0443.py
+++ saleor/account/migrations/0040_auto_20200415_0443.py
@@ -6,6 +6,7 @@
 def change_extension_permission_to_plugin_permission(apps, schema_editor):
     permission = apps.get_model("auth", "Permission")
     users = apps.get_model("account", "User")
+    service_account = apps.get_model("account", "ServiceAccount")

     plugin_permission = permission.objects.filter(
         codename="manage_plugins", content_type__app_label="plugins"
@@ -17,6 +18,10 @@
         user_permissions__content_type__app_label="extensions",
         user_permissions__codename="manage_plugins",
     )
+    service_accounts = service_account.objects.filter(
+        permissions__content_type__app_label="extensions",
+        permissions__codename="manage_plugins",
+    )

     if not plugin_permission or not extension_permission:
         return
@@ -24,6 +29,10 @@
     for user in users:
         user.user_permissions.remove(extension_permission)
         user.user_permissions.add(plugin_permission)
+
+    for service_account in service_accounts:
+        service_account.permissions.remove(extension_permission)
+        service_account.permissions.add(plugin_permission)

     if extension_permission:
         extension_permission.delete()

<|original_code|>
# Generated by Django 3.0.5 on 2020-04-15 09:43

from django.db import migrations

def change_extension_permission_to_plugin_permission(apps, schema_editor):
    permission = apps.get_model("auth", "Permission")
    users = apps.get_model("account", "User")

    plugin_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="plugins"
    ).first()
    extension_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="extensions"
    ).first()
    users = users.objects.filter(
        user_permissions__content_type__app_label="extensions",
        user_permissions__codename="manage_plugins",
    )

    if not plugin_permission or not extension_permission:
        return

    for user in users:
        user.user_permissions.remove(extension_permission)
        user.user_permissions.add(plugin_permission)

    if extension_permission:
        extension_permission.delete()

class Migration(migrations.Migration):

    dependencies = [
        ("account", "0039_auto_20200221_0257"),
        ("plugins", "0001_initial"),
    ]

    operations = [
        migrations.RunPython(change_extension_permission_to_plugin_permission),
    ]

<|edits_diff|>
--- saleor/account/migrations/0040_auto_20200415_0443.py
+++ saleor/account/migrations/0040_auto_20200415_0443.py
@@ -6,6 +6,7 @@
 def change_extension_permission_to_plugin_permission(apps, schema_editor):
     permission = apps.get_model("auth", "Permission")
     users = apps.get_model("account", "User")
+    service_account = apps.get_model("account", "ServiceAccount")

     plugin_permission = permission.objects.filter(
         codename="manage_plugins", content_type__app_label="plugins"
@@ -16,6 +17,10 @@
     users = users.objects.filter(
         user_permissions__content_type__app_label="extensions",
         user_permissions__codename="manage_plugins",
+    )
+    service_accounts = service_account.objects.filter(
+        permissions__content_type__app_label="extensions",
+        permissions__codename="manage_plugins",
     )

     if not plugin_permission or not extension_permission:
<|current_version|>
# Generated by Django 3.0.5 on 2020-04-15 09:43

from django.db import migrations

def change_extension_permission_to_plugin_permission(apps, schema_editor):
    permission = apps.get_model("auth", "Permission")
    users = apps.get_model("account", "User")
    service_account = apps.get_model("account", "ServiceAccount")

    plugin_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="plugins"
    ).first()
    extension_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="extensions"
    ).first()
    users = users.objects.filter(
        user_permissions__content_type__app_label="extensions",
        user_permissions__codename="manage_plugins",
    )
    service_accounts = service_account.objects.filter(
        permissions__content_type__app_label="extensions",
        permissions__codename="manage_plugins",
    )

    if not plugin_permission or not extension_permission:
        return

    for user in users:
        user.user_permissions.remove(extension_permission)
        user.user_permissions.add(plugin_permission)

    if extension_permission:
        extension_permission.delete()

class Migration(migrations.Migration):

    dependencies = [
        ("account", "0039_auto_20200221_0257"),
        ("plugins", "0001_initial"),
    ]

    operations = [
        migrations.RunPython(change_extension_permission_to_plugin_permission),
    ]

<|next_version|>
# Generated by Django 3.0.5 on 2020-04-15 09:43

from django.db import migrations

def change_extension_permission_to_plugin_permission(apps, schema_editor):
    permission = apps.get_model("auth", "Permission")
    users = apps.get_model("account", "User")
    service_account = apps.get_model("account", "ServiceAccount")

    plugin_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="plugins"
    ).first()
    extension_permission = permission.objects.filter(
        codename="manage_plugins", content_type__app_label="extensions"
    ).first()
    users = users.objects.filter(
        user_permissions__content_type__app_label="extensions",
        user_permissions__codename="manage_plugins",
    )
    service_accounts = service_account.objects.filter(
        permissions__content_type__app_label="extensions",
        permissions__codename="manage_plugins",
    )

    if not plugin_permission or not extension_permission:
        return

    for user in users:
        user.user_permissions.remove(extension_permission)
        user.user_permissions.add(plugin_permission)

    for service_account in service_accounts:
        service_account.permissions.remove(extension_permission)
        service_account.permissions.add(plugin_permission)

    if extension_permission:
        extension_permission.delete()

class Migration(migrations.Migration):

    dependencies = [
        ("account", "0039_auto_20200221_0257"),
        ("plugins", "0001_initial"),
    ]

    operations = [
        migrations.RunPython(change_extension_permission_to_plugin_permission),
    ]


Add `add_group` method to `AddressBook` class - to make it possible to add groups to the address book

--- address_book/address_book.py
+++ address_book/address_book.py
@@ -7,9 +7,13 @@

     def __init__(self):
         self.persons = []
+        self.groups = []

     def add_person(self, person):
         self.persons.append(person)
+
+    def add_group(self, group):
+        self.groups.append(group)

     def __contains__(self, item):
         if isinstance(item, Person):

<|original_code|>
from person import Person

__all__ = ['AddressBook']

class AddressBook(object):

    def __init__(self):
        self.persons = []

    def add_person(self, person):
        self.persons.append(person)

    def __contains__(self, item):
        if isinstance(item, Person):
            return item in self.persons
        return False

<|edits_diff|>
--- address_book/address_book.py
+++ address_book/address_book.py
@@ -7,6 +7,7 @@

     def __init__(self):
         self.persons = []
+        self.groups = []

     def add_person(self, person):
         self.persons.append(person)
<|current_version|>
from person import Person

__all__ = ['AddressBook']

class AddressBook(object):

    def __init__(self):
        self.persons = []
        self.groups = []

    def add_person(self, person):
        self.persons.append(person)

    def __contains__(self, item):
        if isinstance(item, Person):
            return item in self.persons
        return False

<|next_version|>
from person import Person

__all__ = ['AddressBook']

class AddressBook(object):

    def __init__(self):
        self.persons = []
        self.groups = []

    def add_person(self, person):
        self.persons.append(person)

    def add_group(self, group):
        self.groups.append(group)

    def __contains__(self, item):
        if isinstance(item, Person):
            return item in self.persons
        return False


Raise exception when --debug is specified to main script

I.e., instead of printing the exception and then exiting.

--- runcommands/__main__.py
+++ runcommands/__main__.py
@@ -7,15 +7,21 @@

 def main(argv=None):
+    debug = None
     try:
         all_argv, run_argv, command_argv = partition_argv(argv)
         cli_args = run.parse_args(RawConfig(run=RunConfig()), run_argv)
         run_args = read_run_args(run)
         run_args.update(cli_args)
+        debug = run_args.get('debug', run.parameters['debug'].default)
         run.implementation(
             None, all_argv=all_argv, run_argv=run_argv, command_argv=command_argv,
             cli_args=cli_args, **run_args)
     except RunCommandsError as exc:
+        if debug or debug is None:
+            # User specified --debug OR processing didn't get far enough
+            # to determine whether user specified --debug.
+            raise
         printer.error(exc, file=sys.stderr)
         return 1
     return 0

<|original_code|>
import sys

from .config import RawConfig, RunConfig
from .exc import RunCommandsError
from .run import run, partition_argv, read_run_args
from .util import printer

def main(argv=None):
    try:
        all_argv, run_argv, command_argv = partition_argv(argv)
        cli_args = run.parse_args(RawConfig(run=RunConfig()), run_argv)
        run_args = read_run_args(run)
        run_args.update(cli_args)
        run.implementation(
            None, all_argv=all_argv, run_argv=run_argv, command_argv=command_argv,
            cli_args=cli_args, **run_args)
    except RunCommandsError as exc:
        printer.error(exc, file=sys.stderr)
        return 1
    return 0

if __name__ == '__main__':
    sys.exit(main())

<|edits_diff|>
--- runcommands/__main__.py
+++ runcommands/__main__.py
@@ -7,11 +7,13 @@

 def main(argv=None):
+    debug = None
     try:
         all_argv, run_argv, command_argv = partition_argv(argv)
         cli_args = run.parse_args(RawConfig(run=RunConfig()), run_argv)
         run_args = read_run_args(run)
         run_args.update(cli_args)
+        debug = run_args.get('debug', run.parameters['debug'].default)
         run.implementation(
             None, all_argv=all_argv, run_argv=run_argv, command_argv=command_argv,
             cli_args=cli_args, **run_args)
<|current_version|>
import sys

from .config import RawConfig, RunConfig
from .exc import RunCommandsError
from .run import run, partition_argv, read_run_args
from .util import printer

def main(argv=None):
    debug = None
    try:
        all_argv, run_argv, command_argv = partition_argv(argv)
        cli_args = run.parse_args(RawConfig(run=RunConfig()), run_argv)
        run_args = read_run_args(run)
        run_args.update(cli_args)
        debug = run_args.get('debug', run.parameters['debug'].default)
        run.implementation(
            None, all_argv=all_argv, run_argv=run_argv, command_argv=command_argv,
            cli_args=cli_args, **run_args)
    except RunCommandsError as exc:
        printer.error(exc, file=sys.stderr)
        return 1
    return 0

if __name__ == '__main__':
    sys.exit(main())

<|next_version|>
import sys

from .config import RawConfig, RunConfig
from .exc import RunCommandsError
from .run import run, partition_argv, read_run_args
from .util import printer

def main(argv=None):
    debug = None
    try:
        all_argv, run_argv, command_argv = partition_argv(argv)
        cli_args = run.parse_args(RawConfig(run=RunConfig()), run_argv)
        run_args = read_run_args(run)
        run_args.update(cli_args)
        debug = run_args.get('debug', run.parameters['debug'].default)
        run.implementation(
            None, all_argv=all_argv, run_argv=run_argv, command_argv=command_argv,
            cli_args=cli_args, **run_args)
    except RunCommandsError as exc:
        if debug or debug is None:
            # User specified --debug OR processing didn't get far enough
            # to determine whether user specified --debug.
            raise
        printer.error(exc, file=sys.stderr)
        return 1
    return 0

if __name__ == '__main__':
    sys.exit(main())


Add account_id as the element of this class

--- kamboo/core.py
+++ kamboo/core.py
@@ -10,8 +10,10 @@
     session = botocore.session.get_session()

     def __init__(self, service_name="ec2", region_name="us-east-1",
+                 account_id=None,
                  credentials=None):
         self.region = region_name
+        self.account_id = account_id
         self.credentials = credentials
         if self.credentials:
             self.session.set_credentials(**self.credentials)

<|original_code|>

import botocore
from kotocore.session import Session

class KambooConnection(object):
    """
    Kamboo connection with botocore session initialized
    """
    session = botocore.session.get_session()

    def __init__(self, service_name="ec2", region_name="us-east-1",
                 credentials=None):
        self.region = region_name
        self.credentials = credentials
        if self.credentials:
            self.session.set_credentials(**self.credentials)
        Connection = Session(session=self.session).get_connection(service_name)
        self.conn = Connection(region_name=self.region)

<|edits_diff|>
--- kamboo/core.py
+++ kamboo/core.py
@@ -10,6 +10,7 @@
     session = botocore.session.get_session()

     def __init__(self, service_name="ec2", region_name="us-east-1",
+                 account_id=None,
                  credentials=None):
         self.region = region_name
         self.credentials = credentials
<|current_version|>

import botocore
from kotocore.session import Session

class KambooConnection(object):
    """
    Kamboo connection with botocore session initialized
    """
    session = botocore.session.get_session()

    def __init__(self, service_name="ec2", region_name="us-east-1",
                 account_id=None,
                 credentials=None):
        self.region = region_name
        self.credentials = credentials
        if self.credentials:
            self.session.set_credentials(**self.credentials)
        Connection = Session(session=self.session).get_connection(service_name)
        self.conn = Connection(region_name=self.region)

<|next_version|>

import botocore
from kotocore.session import Session

class KambooConnection(object):
    """
    Kamboo connection with botocore session initialized
    """
    session = botocore.session.get_session()

    def __init__(self, service_name="ec2", region_name="us-east-1",
                 account_id=None,
                 credentials=None):
        self.region = region_name
        self.account_id = account_id
        self.credentials = credentials
        if self.credentials:
            self.session.set_credentials(**self.credentials)
        Connection = Session(session=self.session).get_connection(service_name)
        self.conn = Connection(region_name=self.region)