<commit_before>#
#    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 oslo_log import log as logging
import six

from heat.common import exception
from heat.common.i18n import _
from heat.common.i18n import _LE
from heat.common.i18n import _LW
from heat.engine.resources import signal_responder

LOG = logging.getLogger(__name__)

class BaseWaitConditionHandle(signal_responder.SignalResponder):
    """Base WaitConditionHandle resource.

    The main point of this class is to :
    - have no dependencies (so the instance can reference it)
    - create credentials to allow for signalling from the instance.
    - handle signals from the instance, validate and store result
    """
    properties_schema = {}

    WAIT_STATUSES = (
        STATUS_FAILURE,
        STATUS_SUCCESS,
    ) = (
        'FAILURE',
        'SUCCESS',
    )

    def handle_create(self):
        super(BaseWaitConditionHandle, self).handle_create()
        self.resource_id_set(self._get_user_id())

    def _status_ok(self, status):
        return status in self.WAIT_STATUSES

    def _metadata_format_ok(self, metadata):
        if sorted(tuple(six.iterkeys(metadata))) == sorted(self.METADATA_KEYS):
            return self._status_ok(metadata[self.STATUS])

    def normalise_signal_data(self, signal_data, latest_metadata):
        return signal_data

    def handle_signal(self, details=None):
        write_attempts = []

        def merge_signal_metadata(signal_data, latest_rsrc_metadata):
            signal_data = self.normalise_signal_data(signal_data,
                                                     latest_rsrc_metadata)

            if not self._metadata_format_ok(signal_data):
                LOG.error(_LE("Metadata failed validation for %s"), self.name)
                raise ValueError(_("Metadata format invalid"))

            new_entry = signal_data.copy()
            unique_id = new_entry.pop(self.UNIQUE_ID)

            new_rsrc_metadata = latest_rsrc_metadata.copy()
            if unique_id in new_rsrc_metadata:
                LOG.warning(_LW("Overwriting Metadata item for id %s!"),
                            unique_id)
            new_rsrc_metadata.update({unique_id: new_entry})

            write_attempts.append(signal_data)
            return new_rsrc_metadata

        self.metadata_set(details, merge_metadata=merge_signal_metadata)

        data_written = write_attempts[-1]
        signal_reason = ('status:%s reason:%s' %
                         (data_written[self.STATUS],
                          data_written[self.REASON]))
        return signal_reason

    def get_status(self):
        """Return a list of the Status values for the handle signals."""
        return [v[self.STATUS]
                for v in six.itervalues(self.metadata_get(refresh=True))]

    def get_status_reason(self, status):
        """Return a list of reasons associated with a particular status."""
        return [v[self.REASON]
                for v in six.itervalues(self.metadata_get(refresh=True))
                if v[self.STATUS] == status]

class WaitConditionFailure(exception.Error):
    def __init__(self, wait_condition, handle):
        reasons = handle.get_status_reason(handle.STATUS_FAILURE)
        super(WaitConditionFailure, self).__init__(';'.join(reasons))

class WaitConditionTimeout(exception.Error):
    def __init__(self, wait_condition, handle):
        reasons = handle.get_status_reason(handle.STATUS_SUCCESS)
        vals = {'len': len(reasons),
                'count': wait_condition.properties[wait_condition.COUNT]}
        if reasons:
            vals['reasons'] = ';'.join(reasons)
            message = (_('%(len)d of %(count)d received - %(reasons)s') % vals)
        else:
            message = (_('%(len)d of %(count)d received') % vals)
        super(WaitConditionTimeout, self).__init__(message)
<commit_msg>Downgrade WaitCondition logs<commit_after>#
#    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 oslo_log import log as logging
import six

from heat.common import exception
from heat.common.i18n import _
from heat.common.i18n import _LI
from heat.engine.resources import signal_responder

LOG = logging.getLogger(__name__)

class BaseWaitConditionHandle(signal_responder.SignalResponder):
    """Base WaitConditionHandle resource.

    The main point of this class is to :
    - have no dependencies (so the instance can reference it)
    - create credentials to allow for signalling from the instance.
    - handle signals from the instance, validate and store result
    """
    properties_schema = {}

    WAIT_STATUSES = (
        STATUS_FAILURE,
        STATUS_SUCCESS,
    ) = (
        'FAILURE',
        'SUCCESS',
    )

    def handle_create(self):
        super(BaseWaitConditionHandle, self).handle_create()
        self.resource_id_set(self._get_user_id())

    def _status_ok(self, status):
        return status in self.WAIT_STATUSES

    def _metadata_format_ok(self, metadata):
        if sorted(tuple(six.iterkeys(metadata))) == sorted(self.METADATA_KEYS):
            return self._status_ok(metadata[self.STATUS])

    def normalise_signal_data(self, signal_data, latest_metadata):
        return signal_data

    def handle_signal(self, details=None):
        write_attempts = []

        def merge_signal_metadata(signal_data, latest_rsrc_metadata):
            signal_data = self.normalise_signal_data(signal_data,
                                                     latest_rsrc_metadata)

            if not self._metadata_format_ok(signal_data):
                LOG.info(_LI("Metadata failed validation for %s"), self.name)
                raise ValueError(_("Metadata format invalid"))

            new_entry = signal_data.copy()
            unique_id = new_entry.pop(self.UNIQUE_ID)

            new_rsrc_metadata = latest_rsrc_metadata.copy()
            if unique_id in new_rsrc_metadata:
                LOG.info(_LI("Overwriting Metadata item for id %s!"),
                         unique_id)
            new_rsrc_metadata.update({unique_id: new_entry})

            write_attempts.append(signal_data)
            return new_rsrc_metadata

        self.metadata_set(details, merge_metadata=merge_signal_metadata)

        data_written = write_attempts[-1]
        signal_reason = ('status:%s reason:%s' %
                         (data_written[self.STATUS],
                          data_written[self.REASON]))
        return signal_reason

    def get_status(self):
        """Return a list of the Status values for the handle signals."""
        return [v[self.STATUS]
                for v in six.itervalues(self.metadata_get(refresh=True))]

    def get_status_reason(self, status):
        """Return a list of reasons associated with a particular status."""
        return [v[self.REASON]
                for v in six.itervalues(self.metadata_get(refresh=True))
                if v[self.STATUS] == status]

class WaitConditionFailure(exception.Error):
    def __init__(self, wait_condition, handle):
        reasons = handle.get_status_reason(handle.STATUS_FAILURE)
        super(WaitConditionFailure, self).__init__(';'.join(reasons))

class WaitConditionTimeout(exception.Error):
    def __init__(self, wait_condition, handle):
        reasons = handle.get_status_reason(handle.STATUS_SUCCESS)
        vals = {'len': len(reasons),
                'count': wait_condition.properties[wait_condition.COUNT]}
        if reasons:
            vals['reasons'] = ';'.join(reasons)
            message = (_('%(len)d of %(count)d received - %(reasons)s') % vals)
        else:
            message = (_('%(len)d of %(count)d received') % vals)
        super(WaitConditionTimeout, self).__init__(message)
<|endoftext|>


<commit_before># coding=utf-8

from NLPlexRemote import Language
import re

class English(Language):

    def and_phrase(self):
        return ' and '

    def or_phrase(self):
        return ' or '

    def decade_plural_phrase(self):
        return 's'

    def regular_expressions(self):
        an = ' (an?y? )?'
        of = ' (of|from) '
        ofin = ' (of|from|in) '

        genre_movie = self.indicate_movie('(movies?|' + self.genre + '( movies?)?)')
        episode = self.indicate_tv('episodes?')

        navi = self.indicate_navigation('go( ?to)?')
        play = self.indicate_play('(play|put on)')
        follow_up = self.indicate_follow_up('(restrict|filter)')
        cmd = '(' + navi + '|' + play + '|' + follow_up + ')' + an

        newest = self.indicate_newest('(the )?newest ')
        unseen = self.indicate_unseen('(unseen|new) ')
        newest_unseen = '(' + newest + '|' + unseen + ')?'

        time = '(the )?((year )?' + self.year + '|(decade )?' + self.decade + 's?)'

        change = '(other |next |different |switch |toggle |change )'

        return [
            # Navigation
            (70, re.compile(self.indicate_on_screen_display('^osd$'), re.I)),
            (70, re.compile(self.indicate_main_menu('^stop.*'), re.I)),
            (80, re.compile(self.indicate_main_menu('(go |goto |go to )?(dashboard|home|menu|menü|home menu)'), re.I)),
            (80, re.compile(self.indicate_jump_backward('(jump |step )*back(wards?)?'), re.I)),
            (80, re.compile(self.indicate_jump_forward('(jump |step )*forwards?'), re.I)),
            (80, re.compile(self.indicate_pause_toggle('pause( episode| movie)?'), re.I)),
            (80, re.compile(self.indicate_subtitle_on('(turn |switch )?subtitles? on'), re.I)),
            (80, re.compile(self.indicate_subtitle_off('(turn |switch )?subtitles? off'), re.I)),
            (80, re.compile(self.indicate_subtitle_toggle(change + 'subtitles?'), re.I)),
            (80, re.compile(self.indicate_language_toggle(change + 'languages?'), re.I)),
            (80, re.compile(self.indicate_play_it('^play( it)?$'), re.I)),
            (80, re.compile(self.indicate_another_choice('(choose )?an ?other( one)?'), re.I)),
            # TV
            (70, re.compile(cmd + newest_unseen + episode + of + self.title + ofin + 'season ' + self.season, re.I)),
            (70, re.compile(cmd + newest_unseen + episode + ofin + 'season ' + self.season + of + self.title + '$', re.I)),
            (60, re.compile(cmd + newest_unseen + episode + of + self.title + '$', re.I)),
            (60, re.compile(cmd + newest_unseen + episode + ' with' + an + self.actor, re.I)),
            (30, re.compile(cmd + newest_unseen + episode + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + episode + ' with' + an + self.actor + of + time, re.I)),
            (30, re.compile(cmd + newest_unseen + episode + of + self.title + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + episode + '$', re.I)),
            # Movies:
            (50, re.compile(cmd + newest_unseen + genre_movie + ' with' + an + self.actor, re.I)),
            (40, re.compile(cmd + newest_unseen + genre_movie + of + '(the )?(director )?' + self.director, re.I)),
            (30, re.compile(cmd + newest_unseen + genre_movie + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with' + an + self.actor + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with( a)?( better| higher)? rating( above| better| higher| over)? (as|than|then) ' + self.higher_than_rating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with( a)?( worse| lower)? rating( below| worse| lower| under)? (as|than|then) ' + self.lower_than_rating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' (with( a)? content rating( of)?| (which|who) are rated) ' + self.contentRating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' rated ' + self.contentRating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + '$', re.I)),
            (20, re.compile(cmd + self.contentRating + ' rated ' + newest_unseen + genre_movie, re.I)),
            # General search:
            (10, re.compile(cmd + self.title + '$', re.I))
        ]
<commit_msg>add 'unknown' synonym for unwatched<commit_after># coding=utf-8

from NLPlexRemote import Language
import re

class English(Language):

    def and_phrase(self):
        return ' and '

    def or_phrase(self):
        return ' or '

    def decade_plural_phrase(self):
        return 's'

    def regular_expressions(self):
        an = ' (an?y? |the )?'
        of = ' (of|from) '
        ofin = ' (of|from|in) '

        genre_movie = self.indicate_movie('(movies?|' + self.genre + '( movies?)?)')
        episode = self.indicate_tv('episodes?')

        navi = self.indicate_navigation('go( ?to)?')
        play = self.indicate_play('(play|put on)')
        follow_up = self.indicate_follow_up('(restrict|filter)')
        cmd = '(' + navi + '|' + play + '|' + follow_up + ')' + an

        newest = self.indicate_newest('(the )?newest ')
        unseen = self.indicate_unseen('(unseen|new|unknown) ')
        newest_unseen = '(' + newest + '|' + unseen + ')?'

        time = '(the )?((year )?' + self.year + '|(decade )?' + self.decade + 's?)'

        change = '(other |next |different |switch |toggle |change )'

        return [
            # Navigation
            (70, re.compile(self.indicate_on_screen_display('^osd$'), re.I)),
            (70, re.compile(self.indicate_main_menu('^stop.*'), re.I)),
            (80, re.compile(self.indicate_main_menu('(go |goto |go to )?(dashboard|home|menu|menü|home menu)'), re.I)),
            (80, re.compile(self.indicate_jump_backward('(jump |step )*back(wards?)?'), re.I)),
            (80, re.compile(self.indicate_jump_forward('(jump |step )*forwards?'), re.I)),
            (80, re.compile(self.indicate_pause_toggle('pause( episode| movie)?'), re.I)),
            (80, re.compile(self.indicate_subtitle_on('(turn |switch )?subtitles? on'), re.I)),
            (80, re.compile(self.indicate_subtitle_off('(turn |switch )?subtitles? off'), re.I)),
            (80, re.compile(self.indicate_subtitle_toggle(change + 'subtitles?'), re.I)),
            (80, re.compile(self.indicate_language_toggle(change + 'languages?'), re.I)),
            (80, re.compile(self.indicate_play_it('^play( it)?$'), re.I)),
            (80, re.compile(self.indicate_another_choice('(choose )?an ?other( one)?'), re.I)),
            # TV
            (70, re.compile(cmd + newest_unseen + episode + of + self.title + ofin + 'season ' + self.season, re.I)),
            (70, re.compile(cmd + newest_unseen + episode + ofin + 'season ' + self.season + of + self.title + '$', re.I)),
            (60, re.compile(cmd + newest_unseen + episode + of + self.title + '$', re.I)),
            (60, re.compile(cmd + newest_unseen + episode + ' with' + an + self.actor, re.I)),
            (30, re.compile(cmd + newest_unseen + episode + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + episode + ' with' + an + self.actor + of + time, re.I)),
            (30, re.compile(cmd + newest_unseen + episode + of + self.title + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + episode + '$', re.I)),
            # Movies:
            (50, re.compile(cmd + newest_unseen + genre_movie + ' with' + an + self.actor, re.I)),
            (40, re.compile(cmd + newest_unseen + genre_movie + of + '(the )?(director )?' + self.director, re.I)),
            (30, re.compile(cmd + newest_unseen + genre_movie + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with' + an + self.actor + of + time, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with( a)?( better| higher)? rating( above| better| higher| over)? (as|than|then) ' + self.higher_than_rating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' with( a)?( worse| lower)? rating( below| worse| lower| under)? (as|than|then) ' + self.lower_than_rating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' (with( a)? content rating( of)?| (which|who) are rated) ' + self.contentRating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + ' rated ' + self.contentRating, re.I)),
            (20, re.compile(cmd + newest_unseen + genre_movie + '$', re.I)),
            (20, re.compile(cmd + self.contentRating + ' rated ' + newest_unseen + genre_movie, re.I)),
            # General search:
            (10, re.compile(cmd + self.title + '$', re.I))
        ]
<|endoftext|>


<commit_before># Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Dictionary of configuration types for cbuildbot.

Each dictionary entry is in turn a dictionary of config_param->value.

config_param's:
board -- The board of the image to build.

master -- This bot pushes changes to the overlays.
important -- Master bot uses important bots to determine overall status.
             i.e. if master bot succeeds and other important slaves succeed
             then the master will uprev packages.  This should align
             with info vs. closer except for the master.and options.tests
hostname -- Needed for 'important' slaves.  The hostname of the bot.  Should
            match hostname in slaves.cfg in buildbot checkout.

uprev -- Uprevs the local ebuilds to build new changes since last stable.
         build.  If master then also pushes these changes on success.
rev_overlays -- Select what overlays to look at for revving. This can be
                'public', 'private' or 'both'.
push_overlays -- Select what overlays to push at. This should be a subset of
                 rev_overlays for the particular builder.  Must be None if
                 not a master.  There should only be one master bot pushing
                 changes to each overlay per branch.

chrome_tests -- runs chrome testing binaries in a vm.

unittests -- Runs unittests for packages.
quick_unit -- If unittests is true, only run the unit tests for packages which
              have changed since the previous build.

vm_tests -- Runs the smoke suite and au test harness in a qemu-based VM
            using KVM.
quick_vm -- If vm_tests is true, run a minimal au test harness suite.

usepkg -- Use binary packages to bootstrap, when possible. (emerge --usepkg)
chroot_replace -- wipe and replace chroot, but not source.

build_type -- Upload prebuilts under the specified category. Can be any of
              [preflight|full|chrome].
test_mod -- Create a test mod image for archival.
factory_install_mod -- Create a factory install image for archival.
factory_test_mod -- Create a factory test image for archival.
"""

# TODO(dgarrett) Make test_mod, factory_install_mod, factory_test_mod options
# go away when these options work for arm.

default = {
  # 'board' No default value

  'master' : False,
  'important' : False,
  # 'hostname' No default value

  'uprev' : False,
  'rev_overlays': 'public',
  'push_overlays': None,

  'chrome_tests' : False,

  'unittests' : True,
  'quick_unit' : True,

  'vm_tests' : True,
  'quick_vm' : True,

  'usepkg' : True,
  'chroot_replace' : False,

  'build_type' : False,
  'archive_build_debug' : False,

  'test_mod' : False,
  'factory_install_mod' : False,
  'factory_test_mod' : False,
}

arm = {
  # VM/tests are broken on arm.
  'unittests' : False,
  'vm_tests' : False,

  # These images don't work for arm.
  'factory_install_mod' : False,
  'factory_test_mod' : False,
}

full = {
  # Full builds are test build to show that we can build from scratch,
  # so use settings to build from scratch, and archive the results.
  'usepkg' : False,
  'chroot_replace' : True,

  'quick_unit' : False,
  'quick_vm' : True,

  'build_type': 'full',
  'archive_build_debug' : True,
  'test_mod' : True,
  'factory_install_mod' : True,
  'factory_test_mod' : True,
}

config = {}

config['x86-generic-pre-flight-queue'] = default.copy()
config['x86-generic-pre-flight-queue'].update({
  'board' : 'x86-generic',
  'master' : True,
  'hostname' : 'chromeosbuild2',

  'uprev' : True,
  'build_type': 'preflight',
  'rev_overlays': 'public',
  'push_overlays': 'public',
})

config['x86-generic-chrome-pre-flight-queue'] = default.copy()
config['x86-generic-chrome-pre-flight-queue'].update({
  'board' : 'x86-generic',
  'master' : True,

  'build_type': 'chrome',
  'uprev' : False,
  'chrome_tests' : True,
  'rev_overlays': 'public',
  'push_overlays': 'public',
})

config['x86-mario-pre-flight-queue'] = default.copy()
config['x86-mario-pre-flight-queue'].update({
  'board' : 'x86-mario',
  'master' : True,

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': 'private',
})

config['x86-mario-pre-flight-branch'] = default.copy()
config['x86-mario-pre-flight-branch'].update({
  'board' : 'x86-mario',
  'master' : True,

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': 'both',
})

config['x86-agz-bin'] = default.copy()
config['x86-agz-bin'].update({
  'board' : 'x86-agz',

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': None,
})

config['x86-dogfood-bin'] = default.copy()
config['x86-dogfood-bin'].update({
  'board' : 'x86-dogfood',

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': None,
})

config['x86-pineview-bin'] = default.copy()
config['x86-pineview-bin'].update({
  'board' : 'x86-pineview',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-tegra2-bin'] = default.copy()
config['arm-tegra2-bin'].update(arm)
config['arm-tegra2-bin'].update({
  'board' : 'tegra2_dev-board',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-generic-bin'] = default.copy()
config['arm-generic-bin'].update(arm)
config['arm-generic-bin'].update({
  'board' : 'arm-generic',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-generic-full'] = default.copy()
config['arm-generic-full'].update(arm)
config['arm-generic-full'].update(full)
config['arm-generic-full'].update({
  'board' : 'arm-generic',
})

config['arm-tegra2-full'] = default.copy()
config['arm-tegra2-full'].update(arm)
config['arm-tegra2-full'].update(full)
config['arm-tegra2-full'].update({
  'board' : 'tegra2_dev-board',
})

config['arm-tegra2-seaboard-full'] = default.copy()
config['arm-tegra2-seaboard-full'].update(arm)
config['arm-tegra2-seaboard-full'].update(full)
config['arm-tegra2-seaboard-full'].update({
  'board' : 'tegra2_seaboard',
})

config['x86-generic-full'] = default.copy()
config['x86-generic-full'].update(full)
config['x86-generic-full'].update({
  'board' : 'x86-generic',
})

config['x86-pineview-full'] = default.copy()
config['x86-pineview-full'].update(full)
config['x86-pineview-full'].update({
  'board' : 'x86-pineview',
})
<commit_msg>Add in an x86-alex chrome preflight queue that builds internal but does not rev anything<commit_after># Copyright (c) 2010 The Chromium OS Authors. All rights reserved.
# Use of this source code is governed by a BSD-style license that can be
# found in the LICENSE file.

"""Dictionary of configuration types for cbuildbot.

Each dictionary entry is in turn a dictionary of config_param->value.

config_param's:
board -- The board of the image to build.

master -- This bot pushes changes to the overlays.
important -- Master bot uses important bots to determine overall status.
             i.e. if master bot succeeds and other important slaves succeed
             then the master will uprev packages.  This should align
             with info vs. closer except for the master.and options.tests
hostname -- Needed for 'important' slaves.  The hostname of the bot.  Should
            match hostname in slaves.cfg in buildbot checkout.

uprev -- Uprevs the local ebuilds to build new changes since last stable.
         build.  If master then also pushes these changes on success.
rev_overlays -- Select what overlays to look at for revving. This can be
                'public', 'private' or 'both'.
push_overlays -- Select what overlays to push at. This should be a subset of
                 rev_overlays for the particular builder.  Must be None if
                 not a master.  There should only be one master bot pushing
                 changes to each overlay per branch.

chrome_tests -- runs chrome testing binaries in a vm.

unittests -- Runs unittests for packages.
quick_unit -- If unittests is true, only run the unit tests for packages which
              have changed since the previous build.

vm_tests -- Runs the smoke suite and au test harness in a qemu-based VM
            using KVM.
quick_vm -- If vm_tests is true, run a minimal au test harness suite.

usepkg -- Use binary packages to bootstrap, when possible. (emerge --usepkg)
chroot_replace -- wipe and replace chroot, but not source.

build_type -- Upload prebuilts under the specified category. Can be any of
              [preflight|full|chrome].
test_mod -- Create a test mod image for archival.
factory_install_mod -- Create a factory install image for archival.
factory_test_mod -- Create a factory test image for archival.
"""

# TODO(dgarrett) Make test_mod, factory_install_mod, factory_test_mod options
# go away when these options work for arm.

default = {
  # 'board' No default value

  'master' : False,
  'important' : False,
  # 'hostname' No default value

  'uprev' : False,
  'rev_overlays': 'public',
  'push_overlays': None,

  'chrome_tests' : False,

  'unittests' : True,
  'quick_unit' : True,

  'vm_tests' : True,
  'quick_vm' : True,

  'usepkg' : True,
  'chroot_replace' : False,

  'build_type' : False,
  'archive_build_debug' : False,

  'test_mod' : False,
  'factory_install_mod' : False,
  'factory_test_mod' : False,
}

arm = {
  # VM/tests are broken on arm.
  'unittests' : False,
  'vm_tests' : False,

  # These images don't work for arm.
  'factory_install_mod' : False,
  'factory_test_mod' : False,
}

full = {
  # Full builds are test build to show that we can build from scratch,
  # so use settings to build from scratch, and archive the results.
  'usepkg' : False,
  'chroot_replace' : True,

  'quick_unit' : False,
  'quick_vm' : True,

  'build_type': 'full',
  'archive_build_debug' : True,
  'test_mod' : True,
  'factory_install_mod' : True,
  'factory_test_mod' : True,
}

config = {}

config['x86-generic-pre-flight-queue'] = default.copy()
config['x86-generic-pre-flight-queue'].update({
  'board' : 'x86-generic',
  'master' : True,
  'hostname' : 'chromeosbuild2',

  'uprev' : True,
  'build_type': 'preflight',
  'rev_overlays': 'public',
  'push_overlays': 'public',
})

config['x86-generic-chrome-pre-flight-queue'] = default.copy()
config['x86-generic-chrome-pre-flight-queue'].update({
  'board' : 'x86-generic',
  'master' : True,

  'build_type': 'chrome',
  'uprev' : False,
  'chrome_tests' : True,
  'rev_overlays': 'public',
  'push_overlays': 'public',
})

config['x86-mario-pre-flight-queue'] = default.copy()
config['x86-mario-pre-flight-queue'].update({
  'board' : 'x86-mario',
  'master' : True,

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': 'private',
})

config['x86-alex-pre-flight-branch'] = default.copy()
config['x86-alex-pre-flight-branch'].update({
  'board' : 'x86-alex',
  'master' : True,

  'uprev' : False,
  'rev_overlays': 'both',
  'push_overlays': 'both',
})

config['x86-mario-pre-flight-branch'] = default.copy()
config['x86-mario-pre-flight-branch'].update({
  'board' : 'x86-mario',
  'master' : True,

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': 'both',
})

config['x86-agz-bin'] = default.copy()
config['x86-agz-bin'].update({
  'board' : 'x86-agz',

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': None,
})

config['x86-dogfood-bin'] = default.copy()
config['x86-dogfood-bin'].update({
  'board' : 'x86-dogfood',

  'uprev' : True,
  'rev_overlays': 'both',
  'push_overlays': None,
})

config['x86-pineview-bin'] = default.copy()
config['x86-pineview-bin'].update({
  'board' : 'x86-pineview',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-tegra2-bin'] = default.copy()
config['arm-tegra2-bin'].update(arm)
config['arm-tegra2-bin'].update({
  'board' : 'tegra2_dev-board',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-generic-bin'] = default.copy()
config['arm-generic-bin'].update(arm)
config['arm-generic-bin'].update({
  'board' : 'arm-generic',

  'uprev' : True,
  'rev_overlays': 'public',
  'push_overlays': None,
})

config['arm-generic-full'] = default.copy()
config['arm-generic-full'].update(arm)
config['arm-generic-full'].update(full)
config['arm-generic-full'].update({
  'board' : 'arm-generic',
})

config['arm-tegra2-full'] = default.copy()
config['arm-tegra2-full'].update(arm)
config['arm-tegra2-full'].update(full)
config['arm-tegra2-full'].update({
  'board' : 'tegra2_dev-board',
})

config['arm-tegra2-seaboard-full'] = default.copy()
config['arm-tegra2-seaboard-full'].update(arm)
config['arm-tegra2-seaboard-full'].update(full)
config['arm-tegra2-seaboard-full'].update({
  'board' : 'tegra2_seaboard',
})

config['x86-generic-full'] = default.copy()
config['x86-generic-full'].update(full)
config['x86-generic-full'].update({
  'board' : 'x86-generic',
})

config['x86-pineview-full'] = default.copy()
config['x86-pineview-full'].update(full)
config['x86-pineview-full'].update({
  'board' : 'x86-pineview',
})
<|endoftext|>


<commit_before>#!/usr/bin/python

# This file is part of Espruino, a JavaScript interpreter for Microcontrollers
#
# Copyright (C) 2013 Gordon Williams <gw@pur3.co.uk>
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
#
# ----------------------------------------------------------------------------------------
# Builds HTML documentation for functions from the JSON included in comments in
# jswrap_*.c files
# ----------------------------------------------------------------------------------------

import subprocess;
import re;
import json;
import sys;
import os;
sys.path.append(".");
import common

# Scans files for comments of the form /*JSON......*/ and then writes out an HTML file describing
# all the functions

jsondatas = common.get_jsondata(True)

classes = []
for jsondata in jsondatas:
  if "class" in jsondata:
    if not jsondata["class"] in classes:
      classes.append(jsondata["class"])

# Load list of 'uses' in EspruinoDocs
code_uses = []
referenceFile = "../EspruinoDocs/references.json"
if os.path.isfile(referenceFile):
  print "Found references.json - using this to link to examples"
  code_uses = json.loads(open(referenceFile, "r").read())

# start writing
htmlFile = open('functions.html', 'w')
def html(s): htmlFile.write(s+"\n");

def htmlify(d):
  d = re.sub(r'```([^`]+)```', r'\1', d) # code tags
  d = re.sub(r'`([^`]+)`', r'\1', d) # code tags
  d = re.sub(r'\[([^\]]*)\]\(([^\)]*)\)', r'\1', d) # links tags
  d = re.sub(r'([^">])(http://[^ ]+)', r'\1\2', d) # links tags
  return d

def html_description(ds,current):
  if not isinstance(ds, list): ds = [ ds ]
  for d in ds:
    for link in links:
      if link!=current:
        d = d.replace(" "+link+" ", " "+link+" ")
        d = d.replace(" "+link+".", " "+link+".")
        d = d.replace(" "+link+"(", " "+link+"(")
    html("
"+htmlify(d)+"
")

def get_prefixed_name(jsondata):
  s=""
  if "class" in jsondata:
    s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  return s

def get_fullname(jsondata):
  s = common.get_prefix_name(jsondata)
  if s!="": s = s + " "
  if jsondata["type"]!="constructor":
    if "class" in jsondata:
      s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  return s

def get_arguments(jsondata):
  if common.is_property(jsondata):
    return ""
  args = [];
  if "params" in jsondata:
    for param in jsondata["params"]:
      args.append(param[0]);
      if param[1]=="JsVarArray": args.append("...");
  return "("+", ".join(args)+")"

def get_surround(jsondata):
  s = common.get_prefix_name(jsondata)
  if s!="": s = s + " "
  if jsondata["type"]!="constructor":
    if "class" in jsondata: s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  s=s+get_arguments(jsondata)
  return s

def get_code(jsondata):
  if jsondata["type"]=="event":
    return jsondata["class"]+".on('"+jsondata["name"]+"', function"+get_arguments(jsondata)+" { ... });";
  if jsondata["type"]=="constructor":
    return "new "+jsondata["name"]+get_arguments(jsondata);
  return get_surround(jsondata)

def get_link(jsondata):
  s="l_";
  if "class" in jsondata:
    s=s+jsondata["class"]+"_"
  else:
    s=s+"_global_"
  s=s+jsondata["name"]
  return s

html("")
html(" ")
html("  <title>Espruino Reference</title>")
html("  ")
html(" ")
html(" ")
html("
Espruino Software Reference
")
html("
Version "+common.get_version()+"
")
html("
Contents
")
html("
Globals
")
html("
")
detail = []
links = {}
jsondatas = sorted(jsondatas, key=common.get_name_or_space)
for jsondata in jsondatas:
  if "name" in jsondata and not "class" in jsondata and not jsondata["type"]=="object":
    html("
"+get_surround(jsondata)+"
")
    if not "no_create_links" in jsondata:
      links[get_prefixed_name(jsondata)] = get_link(jsondata)
    detail.append(jsondata)
for className in sorted(classes):
  html("
")
  html("
"+className+"
")
  html("
")
  for jsondata in jsondatas:
    if "name" in jsondata and "class" in jsondata and jsondata["class"]==className:
      html("
"+get_surround(jsondata)+"
")
      if not "no_create_links" in jsondata:
        links[get_prefixed_name(jsondata)] = get_link(jsondata)
      detail.append(jsondata)
html("
")

html("
Detail
")
lastClass = "XXX"
for jsondata in detail:
  className = ""
  niceName = ""
  linkName = ""
  if "class" in jsondata:
    className=jsondata["class"]
    niceName=className+" Class"
    linkName=className
  else:
    className=""
    niceName="Global Functions"
    linkName="_global"

  if className!=lastClass:
    lastClass=className
    html("
"+niceName+"
")
    html("
(top)
")
    for j in jsondatas:
      if (j["type"]=="class" or j["type"]=="library") and j["class"]==className:
        ds = html_description(j["description"], className)

    instances = []
    for j in jsondatas:
      if "instanceof" in j and j["instanceof"]==className:
        instances.append(j)
    if len(instances)>0:
      html("
Instances
")
      html("
")
      for j in instances:
        html("

"+j["name"]+"
");
        html_description(j["description"], j["name"])
        html("
")
      html("
")

    html("
Methods and Fields
")
    html("
")
    for j in jsondatas:
      if ("name" in j) and (className!="" or not "instanceof" in j) and ((className=="" and not "class" in j) or ("class" in j and j["class"]==className)):
        html("
"+get_surround(j)+"
")
    html("
")
  html("
"+get_fullname(jsondata)+"
")
  html("
(top)
")
  html("
Call type:
")
  html("
"+get_code(jsondata)+"
")
  if "description" in jsondata:
    html("
Description
")
    desc = jsondata["description"]
    if not isinstance(desc, list): desc = [ desc ]
    if ("ifdef" in jsondata) or ("ifndef" in jsondata):
      conds = ""
      if "ifdef" in jsondata: conds = common.get_ifdef_description(jsondata["ifdef"])
      if "ifndef" in jsondata:
        if conds!="": conds += " and "
        conds = "not "+common.get_ifdef_description(jsondata["ifndef"])
      desc.append("Note: This is only available in some devices: "+conds);
    html_description(desc, jsondata["name"])
  html("
Parameters
")
  if "params" in jsondata:
    for param in jsondata["params"]:
      desc = ""
      if len(param)>2: desc=param[2]
      if isinstance(desc, list): desc = '
'.join(desc)
      extra = ""
      if  param[1]=="JsVarArray": extra = ", ...";
      html("
 "+param[0]+extra+" "+htmlify(desc)+"
")
  else:
    html("
No parameters
")
  html("
Returns
")
  if "return" in jsondata:
    desc = ""
    if len(jsondata["return"])>1: desc=jsondata["return"][1]
    if desc=="": desc="See description above"
    html("
"+htmlify(desc)+"
")
  else:
    html("
No return value (undefined)
")

  url = "http://www.espruino.com/Reference#"+get_link(jsondata)
  if url in code_uses:
    uses = code_uses[url]
    html("
Examples
")
    html("
This function is used in the following places in Espruino's documentation
")
    html("
")
    for link in uses:
      html('
'+link["title"]+'
')
    html("
")

html(" ")
html("")

# --------------------------------------------------------------------------
#                                                     Write/create keywords
# --------------------------------------------------------------------------
keywords = {}
for j in jsondatas:
  if ("name" in j):
    item = { "title" : get_surround(j), "path": "/Reference#"+get_link(j) };
    jkeywords = [ j["name"] ]
    if get_prefixed_name(j)!=j["name"]: jkeywords.append(get_prefixed_name(j))
    if "class" in j: jkeywords.append(j["class"])

    for k in jkeywords:
      k = k.lower()
      if not k in keywords:
        keywords[k] = [ item ]
      else:
        keywords[k].append(item)

#print(json.dumps(keywords, sort_keys=True, indent=2))
keywordFile = open('function_keywords.js', 'w')
keywordFile.write(json.dumps(keywords, sort_keys=True, indent=2));

# ---------------------------- Just random helper stuff
builtins = []
for jsondata in jsondatas:
  if jsondata["type"]=="staticmethod" or jsondata["type"]=="staticproperty" or jsondata["type"]=="class":
    if not jsondata["class"] in builtins:
      builtins.append(jsondata["class"])
  elif jsondata["type"]=="function" or jsondata["type"]=="variable" or jsondata["type"]=="class":
      if not jsondata["name"] in builtins:
        builtins.append(jsondata["name"])
print "------------------------------------------------------"
print('Global classes and functions: '+' '.join(builtins));
print "------------------------------------------------------"
<commit_msg>add links to MDN for functions that are covered<commit_after>#!/usr/bin/python

# This file is part of Espruino, a JavaScript interpreter for Microcontrollers
#
# Copyright (C) 2013 Gordon Williams <gw@pur3.co.uk>
#
# This Source Code Form is subject to the terms of the Mozilla Public
# License, v. 2.0. If a copy of the MPL was not distributed with this
# file, You can obtain one at http://mozilla.org/MPL/2.0/.
#
# ----------------------------------------------------------------------------------------
# Builds HTML documentation for functions from the JSON included in comments in
# jswrap_*.c files
# ----------------------------------------------------------------------------------------

import subprocess;
import re;
import json;
import sys;
import os;
sys.path.append(".");
import common
import urllib2

# Scans files for comments of the form /*JSON......*/ and then writes out an HTML file describing
# all the functions

jsondatas = common.get_jsondata(True)

classes = []
for jsondata in jsondatas:
  if "class" in jsondata:
    if not jsondata["class"] in classes:
      classes.append(jsondata["class"])

# Load list of 'uses' in EspruinoDocs
code_uses = []
referenceFile = "../EspruinoDocs/references.json"
if os.path.isfile(referenceFile):
  print "Found references.json - using this to link to examples"
  code_uses = json.loads(open(referenceFile, "r").read())

# Load list of MDN URLs (to speed up processing)
valid_mdn_urls = { 'valid' : [], 'invalid' : [] };
mdnURLFile = "MDN_URLS.txt"
if os.path.isfile(mdnURLFile):
  valid_mdn_urls = json.loads(open(mdnURLFile, "r").read())

# start writing
htmlFile = open('functions.html', 'w')
def html(s): htmlFile.write(s+"\n");

def htmlify(d):
  d = re.sub(r'```([^`]+)```', r'\1', d) # code tags
  d = re.sub(r'`([^`]+)`', r'\1', d) # code tags
  d = re.sub(r'\[([^\]]*)\]\(([^\)]*)\)', r'\1', d) # links tags
  d = re.sub(r'([^">])(http://[^ ]+)', r'\1\2', d) # links tags
  return d

def html_description(ds,current):
  if not isinstance(ds, list): ds = [ ds ]
  for d in ds:
    for link in links:
      if link!=current:
        d = d.replace(" "+link+" ", " "+link+" ")
        d = d.replace(" "+link+".", " "+link+".")
        d = d.replace(" "+link+"(", " "+link+"(")
    html("
"+htmlify(d)+"
")

def get_prefixed_name(jsondata):
  s=""
  if "class" in jsondata:
    s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  return s

def get_fullname(jsondata):
  s = common.get_prefix_name(jsondata)
  if s!="": s = s + " "
  if jsondata["type"]!="constructor":
    if "class" in jsondata:
      s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  return s

def get_arguments(jsondata):
  if common.is_property(jsondata):
    return ""
  args = [];
  if "params" in jsondata:
    for param in jsondata["params"]:
      args.append(param[0]);
      if param[1]=="JsVarArray": args.append("...");
  return "("+", ".join(args)+")"

def get_surround(jsondata):
  s = common.get_prefix_name(jsondata)
  if s!="": s = s + " "
  if jsondata["type"]!="constructor":
    if "class" in jsondata: s=s+jsondata["class"]+"."
  s=s+jsondata["name"]
  s=s+get_arguments(jsondata)
  return s

def get_code(jsondata):
  if jsondata["type"]=="event":
    return jsondata["class"]+".on('"+jsondata["name"]+"', function"+get_arguments(jsondata)+" { ... });";
  if jsondata["type"]=="constructor":
    return "new "+jsondata["name"]+get_arguments(jsondata);
  return get_surround(jsondata)

def get_link(jsondata):
  s="l_";
  if "class" in jsondata:
    s=s+jsondata["class"]+"_"
  else:
    s=s+"_global_"
  s=s+jsondata["name"]
  return s

# If MDN doesn't 404 then include a link to it
def insert_mdn_link(jsondata):
  if "class" in jsondata and "name" in jsondata:
    url = "https://developer.mozilla.org/en-US/docs/Web/JavaScript/Reference/Global_Objects/"+jsondata["class"]
    if jsondata["type"]!="constructor": url = url +"/"+jsondata["name"]
    if url in valid_mdn_urls['valid']:
      code = 200
    elif url in valid_mdn_urls['invalid']:
      code = 404
    else:
      print "Checking URL "+url
      try:
        connection = urllib2.urlopen(url)
        code = connection.getcode()
        connection.close()
      except urllib2.HTTPError, e:
        code = e.getcode()
      if code==200: valid_mdn_urls['valid'].append(url)
      else: valid_mdn_urls['invalid'].append(url)
    if code==200:
      html("
View MDN documentation
")

html("")
html(" ")
html("  <title>Espruino Reference</title>")
html("  ")
html(" ")
html(" ")
html("
Espruino Software Reference
")
html("
Version "+common.get_version()+"
")
html("
Contents
")
html("
Globals
")
html("
")
detail = []
links = {}
jsondatas = sorted(jsondatas, key=common.get_name_or_space)
for jsondata in jsondatas:
  if "name" in jsondata and not "class" in jsondata and not jsondata["type"]=="object":
    html("
"+get_surround(jsondata)+"
")
    if not "no_create_links" in jsondata:
      links[get_prefixed_name(jsondata)] = get_link(jsondata)
    detail.append(jsondata)
for className in sorted(classes):
  html("
")
  html("
"+className+"
")
  html("
")
  for jsondata in jsondatas:
    if "name" in jsondata and "class" in jsondata and jsondata["class"]==className:
      html("
"+get_surround(jsondata)+"
")
      if not "no_create_links" in jsondata:
        links[get_prefixed_name(jsondata)] = get_link(jsondata)
      detail.append(jsondata)
html("
")

html("
Detail
")
lastClass = "XXX"
for jsondata in detail:
  className = ""
  niceName = ""
  linkName = ""
  if "class" in jsondata:
    className=jsondata["class"]
    niceName=className+" Class"
    linkName=className
  else:
    className=""
    niceName="Global Functions"
    linkName="_global"

  if className!=lastClass:
    lastClass=className
    html("
"+niceName+"
")
    html("
(top)
")
    for j in jsondatas:
      if (j["type"]=="class" or j["type"]=="library") and j["class"]==className:
        ds = html_description(j["description"], className)

    instances = []
    for j in jsondatas:
      if "instanceof" in j and j["instanceof"]==className:
        instances.append(j)
    if len(instances)>0:
      html("
Instances
")
      html("
")
      for j in instances:
        html("

"+j["name"]+"
");
        html_description(j["description"], j["name"])
        html("
")
      html("
")

    html("
Methods and Fields
")
    html("
")
    for j in jsondatas:
      if ("name" in j) and (className!="" or not "instanceof" in j) and ((className=="" and not "class" in j) or ("class" in j and j["class"]==className)):
        html("
"+get_surround(j)+"
")
    html("
")
  html("
"+get_fullname(jsondata)+"
")
  insert_mdn_link(jsondata);
  html("
(top)
")
  html("
Call type:
")
  html("
"+get_code(jsondata)+"
")
  if "description" in jsondata:
    html("
Description
")
    desc = jsondata["description"]
    if not isinstance(desc, list): desc = [ desc ]
    if ("ifdef" in jsondata) or ("ifndef" in jsondata):
      conds = ""
      if "ifdef" in jsondata: conds = common.get_ifdef_description(jsondata["ifdef"])
      if "ifndef" in jsondata:
        if conds!="": conds += " and "
        conds = "not "+common.get_ifdef_description(jsondata["ifndef"])
      desc.append("Note: This is only available in some devices: "+conds);
    html_description(desc, jsondata["name"])
  html("
Parameters
")
  if "params" in jsondata:
    for param in jsondata["params"]:
      desc = ""
      if len(param)>2: desc=param[2]
      if isinstance(desc, list): desc = '
'.join(desc)
      extra = ""
      if  param[1]=="JsVarArray": extra = ", ...";
      html("
 "+param[0]+extra+" "+htmlify(desc)+"
")
  else:
    html("
No parameters
")
  html("
Returns
")
  if "return" in jsondata:
    desc = ""
    if len(jsondata["return"])>1: desc=jsondata["return"][1]
    if desc=="": desc="See description above"
    html("
"+htmlify(desc)+"
")
  else:
    html("
No return value (undefined)
")

  url = "http://www.espruino.com/Reference#"+get_link(jsondata)
  if url in code_uses:
    uses = code_uses[url]
    html("
Examples
")
    html("
This function is used in the following places in Espruino's documentation
")
    html("
")
    for link in uses:
      html('
'+link["title"]+'
')
    html("
")

html(" ")
html("")

# --------------------------------------------------------------------------
#                                                     Write/create keywords
# --------------------------------------------------------------------------
keywords = {}
for j in jsondatas:
  if ("name" in j):
    item = { "title" : get_surround(j), "path": "/Reference#"+get_link(j) };
    jkeywords = [ j["name"] ]
    if get_prefixed_name(j)!=j["name"]: jkeywords.append(get_prefixed_name(j))
    if "class" in j: jkeywords.append(j["class"])

    for k in jkeywords:
      k = k.lower()
      if not k in keywords:
        keywords[k] = [ item ]
      else:
        keywords[k].append(item)

#print(json.dumps(keywords, sort_keys=True, indent=2))
keywordFile = open('function_keywords.js', 'w')
keywordFile.write(json.dumps(keywords, sort_keys=True, indent=2));

# ---------------------------- Just random helper stuff
builtins = []
for jsondata in jsondatas:
  if jsondata["type"]=="staticmethod" or jsondata["type"]=="staticproperty" or jsondata["type"]=="class":
    if not jsondata["class"] in builtins:
      builtins.append(jsondata["class"])
  elif jsondata["type"]=="function" or jsondata["type"]=="variable" or jsondata["type"]=="class":
      if not jsondata["name"] in builtins:
        builtins.append(jsondata["name"])
print "------------------------------------------------------"
print('Global classes and functions: '+' '.join(builtins));
print "------------------------------------------------------"

# Writing MDN URL file
open(mdnURLFile, "w").write(json.dumps(valid_mdn_urls, sort_keys=True, indent=2))
<|endoftext|>


<commit_before>print "I will now count my chickens:"
print "Hens", 25 + 30 / 6
print "Roosters", 100 - 25 * 3 % 4

print "Now I will count the eggs:"
print 3 + 2 + 1 - 5 + 4 % 2 - 1 / 4 + 6

print "Is it true that 3 + 2 < 5 - 7?"
print 3 + 2 < 5 - 7

print "What is 3 + 2?", 3 + 2
print "What is 5 - 7?", 5 - 7
print "Oh, that's why it's False."

print "How about some more?"
print "Is it greater?", 5 > -2
print "Is it greater or equal?", 5 >= -2
print "Is it less or equal?", 5 <= -2

# Study Drill
print "How many chickens do I possess?"
print 25 + 30 / 6," Hens and", 100 - 25 * 3 % 4, " Roosters."<commit_msg>Updated some calculations to use Floating Point numbers<commit_after>print "I will now count my chickens:"
print "Hens", 25 + 30 / 6
print "Roosters", 100 - 25 * 3 % 4

print "Now I will count the eggs:"
print 3 + 2 + 1 - 5 + 4 % 2 - 1 / 4 + 6

# using floating point numbers - Study Drill
print "Is it true that 3 + 2 < 5 - 7?"
print 3.0 + 2.0 < 5.0 - 7.0

# using floating point numbers - Study Drill
print "What is 3 + 2?", 3 + 2.0
print "What is 5 - 7?", 5 - 7.0
print "Oh, that's why it's False."

print "How about some more?"
print "Is it greater?", 5 > -2
print "Is it greater or equal?", 5 >= -2
print "Is it less or equal?", 5 <= -2

# Study Drill
print "How many chickens do I possess?"
print 25 + 30 / 6," Hens and", 100 - 25 * 3 % 4, " Roosters."<|endoftext|>


<commit_before>import re
import uuid
from StringIO import StringIO

from django.core.management import call_command
from django.core.files.base import ContentFile

import mock
import responses

from cms.models import Post, Category, Localisation
from cms.tests.base import BaseCmsTestCase
from cms.management.commands import import_from_git

from unicore.content import models as eg_models

class TestImportFromGit(BaseCmsTestCase):

    def setUp(self):
        self.workspace = self.mk_workspace()

    def mock_get_image_response(self, host, status=200, body='',
                                content_type='image/png'):
        responses.add(
            responses.GET,
            re.compile(r'%s/image/\w{32}' % host),
            body=body,
            status=status,
            content_type=content_type)

    def mock_get_on_redirect_image_response(self, host, status=200, body='',
                                            content_type='image/png'):
        responses.add(
            responses.GET,
            re.compile(r'%s/image/\w{32}/locales/.+' % host),
            body=body,
            status=status,
            content_type=content_type)

    def mock_create_image_response(self, host, status=201):
        def callback(request):
            return (status, {
                'Location': '/image/%s/%s' %
                    (uuid.uuid4().hex, request.headers['Slug'])}, '')

        responses.add_callback(
            responses.POST, '%s/image' % host, callback=callback)

    @mock.patch.object(import_from_git.Command, 'set_image_field')
    def test_command(self, mock_set_image_field):
        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            lang1 = eg_models.Localisation({'locale': 'spa_ES'})
            lang2 = eg_models.Localisation({
                'locale': 'fra_FR',
                'image': uuid.uuid4().hex,
                'image_host': 'http://localhost:8888',
                'logo_image': uuid.uuid4().hex,
                'logo_image_host': 'http://localhost:8888',
                'logo_text': 'text foo',
                'logo_description': 'description foo'})
            self.workspace.save(lang1, 'Added spanish language')
            self.workspace.save(lang2, 'Added french language')

            cat1, cat2 = self.create_categories(self.workspace, position=3)
            self.workspace.save(cat1.update({
                'source': cat2.uuid,
                'position': 4,
            }), 'Added source to category.')

            pages = self.create_pages(self.workspace, count=10)
            for page in pages[:8]:
                up = page.update({
                    'primary_category': cat1.uuid,
                    'author_tags': ['foo', 'bar', 'baz'],
                })
                self.workspace.save(up, 'Added category.')

            [page0] = self.workspace.S(
                eg_models.Page).filter(uuid=pages[0].uuid)
            original = page0.get_object()
            updated = original.update({
                'linked_pages': [page.uuid for page in pages[:3]],
                'source': pages[4].uuid,
            })
            self.workspace.save(updated, 'Added related fields.')

            self.assertEquals(Category.objects.all().count(), 0)
            self.assertEquals(Post.objects.all().count(), 0)

            call_command('import_from_git', quiet=True)

            self.assertEquals(Category.objects.all().count(), 2)
            self.assertEquals(Post.objects.all().count(), 10)

            c = Category.objects.get(uuid=cat1.uuid)
            self.assertEquals(c.source.uuid, cat2.uuid)
            self.assertEquals(c.position, 4)

            p = Post.objects.get(uuid=page0.uuid)
            self.assertEquals(p.related_posts.count(), 3)
            self.assertEquals(p.primary_category.uuid, cat1.uuid)
            self.assertEquals(p.source.uuid, pages[4].uuid)
            self.assertEquals(
                set(p.author_tags.names()),
                set(['foo', 'bar', 'baz']))

            self.assertEquals(Localisation.objects.all().count(), 3)
            self.assertEquals(mock_set_image_field.call_count, 4)
            l = Localisation.objects.get(
                language_code='fra', country_code='FR')
            self.assertEquals(lang2.logo_text, l.logo_text)
            self.assertEquals(lang2.logo_description, l.logo_description)

    def test_get_input_data(self):

        self.captured_message = None

        def patched_input_func(message):
            self.captured_message = message
            return 'y'

        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.input_func = patched_input_func
            command.handle(quiet=False)

        self.assertEquals(
            self.captured_message,
            'Do you want to delete existing data? Y/n: ')
        self.assertEquals(command.stdout.getvalue(), (
            'deleting existing content..'
            'creating localisations..'
            'creating categories..'
            'creating pages..'
            'done.'))

    def test_get_input_data_with_default(self):

        self.captured_message = None

        def patched_input_func(message):
            self.captured_message = message
            return ''

        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.input_func = patched_input_func
            command.handle(quiet=False)

        self.assertEquals(
            self.captured_message,
            'Do you want to delete existing data? Y/n: ')
        self.assertEquals(command.stdout.getvalue(), (
            'deleting existing content..'
            'creating localisations..'
            'creating categories..'
            'creating pages..'
            'done.'))

    def test_get_input_data_with_quiet_set(self):
        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.handle(quiet=True)
            self.assertEquals(command.stdout.getvalue(), '')

    @responses.activate
    def test_get_thumbor_image_file(self):
        host = 'http://localhost:8888'
        key = uuid.uuid4().hex
        command = import_from_git.Command()
        self.mock_get_image_response(host=host)

        file_obj, content_type = command.get_thumbor_image_file(
            host=host, uuid=key)
        self.assertIsInstance(file_obj, ContentFile)
        self.assertEqual(content_type, 'image/png')

        responses.reset()
        self.mock_get_image_response(host=host, status=404)

        file_obj, content_type = command.get_thumbor_image_file(
            host=host, uuid=key)
        self.assertIs(file_obj, None)
        self.assertIs(file_obj, None)

    @responses.activate
    def test_set_image_field(self):
        command = import_from_git.Command()
        command.stdout = StringIO()
        command.quiet = False
        command.disconnect_signals()

        host = 'http://localhost:8888'
        # 1 x 1 bitmap image
        body = 'BM:\x00\x00\x00\x00\x00\x00\x006\x00\x00\x00(\x00\x00\x00' \
               '\x01\x00\x00\x00\x01\x00\x00\x00\x01\x00\x18\x00\x00\x00' \
               '\x00\x00\x04\x00\x00\x00\x13\x0b\x00\x00\x13\x0b\x00\x00' \
               '\x00\x00\x00\x00\x00\x00\x00\x00\xff\xff\xff\x00'
        content_type = 'image/x-ms-bmp'
        self.mock_get_image_response(
            host=host, content_type=content_type, body=body)
        self.mock_get_on_redirect_image_response(
            host=host, content_type=content_type, body=body)
        self.mock_create_image_response(host=host)

        eg_obj = eg_models.Localisation({
            'locale': 'fra_FR',
            'image': uuid.uuid4().hex,
            'image_host': host})
        db_obj = Localisation.objects.create(
            language_code='fra', country_code='FR')

        command.set_image_field(eg_obj, db_obj, 'image')
        db_obj = Localisation.objects.get(
            language_code='fra', country_code='FR')
        self.assertEqual(command.stdout.getvalue(), '')
        self.assertTrue(
            re.match(r'/image/\w{32}/locales/image.bmp', db_obj.image.name))
        self.assertEqual(db_obj.image_width, 1)
        self.assertEqual(db_obj.image_height, 1)

        responses.reset()
        self.mock_get_image_response(host=host, status=404)
        command.stdout = StringIO()

        command.set_image_field(eg_obj, db_obj, 'image')
        self.assertTrue(command.stdout.getvalue().startswith('WARNING: image'))

        command.stdout = StringIO()
        command.set_image_field(eg_obj, db_obj, 'logo_image')
        self.assertFalse(db_obj.logo_image)

        responses.reset()
        self.mock_get_image_response(host=host, content_type='.bmp')

        with mock.patch.object(db_obj.image, 'save') as mock_save_image:
            command.set_image_field(eg_obj, db_obj, 'image')
            file_name = mock_save_image.call_args[0][0]
            self.assertTrue(file_name.endswith('.bmp'))

        command.reconnect_signals()
<commit_msg>test updated set_image_field method<commit_after>import re
import uuid
from StringIO import StringIO

from django.core.management import call_command
from django.core.files.base import ContentFile

import mock
import responses

from cms.models import Post, Category, Localisation
from cms.tests.base import BaseCmsTestCase
from cms.management.commands import import_from_git

from unicore.content import models as eg_models

class TestImportFromGit(BaseCmsTestCase):

    def setUp(self):
        self.workspace = self.mk_workspace()

    def mock_get_image_response(self, host, status=200, body='',
                                content_type='image/png'):
        responses.add(
            responses.GET,
            re.compile(r'%s/image/\w{32}' % host),
            body=body,
            status=status,
            content_type=content_type)

    def mock_get_on_redirect_image_response(self, host, status=200, body='',
                                            content_type='image/png'):
        responses.add(
            responses.GET,
            re.compile(
                r'%s/image/\w{32}/(locales|posts|categories)/.+' % host),
            body=body,
            status=status,
            content_type=content_type)

    def mock_create_image_response(self, host, status=201):
        def callback(request):
            return (status, {
                'Location': '/image/%s/%s' %
                    (uuid.uuid4().hex, request.headers['Slug'])}, '')

        responses.add_callback(
            responses.POST, '%s/image' % host, callback=callback)

    @mock.patch.object(import_from_git.Command, 'set_image_field')
    def test_command(self, mock_set_image_field):
        mock_set_image_field.return_value = False
        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            lang1 = eg_models.Localisation({'locale': 'spa_ES'})
            lang2 = eg_models.Localisation({
                'locale': 'fra_FR',
                'image': uuid.uuid4().hex,
                'image_host': 'http://localhost:8888',
                'logo_image': uuid.uuid4().hex,
                'logo_image_host': 'http://localhost:8888',
                'logo_text': 'text foo',
                'logo_description': 'description foo'})
            self.workspace.save(lang1, 'Added spanish language')
            self.workspace.save(lang2, 'Added french language')

            cat1, cat2 = self.create_categories(self.workspace, position=3)
            self.workspace.save(cat1.update({
                'source': cat2.uuid,
                'position': 4,
            }), 'Added source to category.')

            pages = self.create_pages(self.workspace, count=10)
            for page in pages[:8]:
                up = page.update({
                    'primary_category': cat1.uuid,
                    'author_tags': ['foo', 'bar', 'baz'],
                })
                self.workspace.save(up, 'Added category.')

            [page0] = self.workspace.S(
                eg_models.Page).filter(uuid=pages[0].uuid)
            original = page0.get_object()
            updated = original.update({
                'linked_pages': [page.uuid for page in pages[:3]],
                'source': pages[4].uuid,
            })
            self.workspace.save(updated, 'Added related fields.')

            self.assertEquals(Category.objects.all().count(), 0)
            self.assertEquals(Post.objects.all().count(), 0)

            call_command('import_from_git', quiet=True)

            self.assertEquals(Category.objects.all().count(), 2)
            self.assertEquals(Post.objects.all().count(), 10)

            c = Category.objects.get(uuid=cat1.uuid)
            self.assertEquals(c.source.uuid, cat2.uuid)
            self.assertEquals(c.position, 4)

            p = Post.objects.get(uuid=page0.uuid)
            self.assertEquals(p.related_posts.count(), 3)
            self.assertEquals(p.primary_category.uuid, cat1.uuid)
            self.assertEquals(p.source.uuid, pages[4].uuid)
            self.assertEquals(
                set(p.author_tags.names()),
                set(['foo', 'bar', 'baz']))

            self.assertEquals(Localisation.objects.all().count(), 3)
            self.assertEquals(mock_set_image_field.call_count, 16)
            l = Localisation.objects.get(
                language_code='fra', country_code='FR')
            self.assertEquals(lang2.logo_text, l.logo_text)
            self.assertEquals(lang2.logo_description, l.logo_description)

    def test_get_input_data(self):

        self.captured_message = None

        def patched_input_func(message):
            self.captured_message = message
            return 'y'

        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.input_func = patched_input_func
            command.handle(quiet=False)

        self.assertEquals(
            self.captured_message,
            'Do you want to delete existing data? Y/n: ')
        self.assertEquals(command.stdout.getvalue(), (
            'deleting existing content..'
            'creating localisations..'
            'creating categories..'
            'creating pages..'
            'done.'))

    def test_get_input_data_with_default(self):

        self.captured_message = None

        def patched_input_func(message):
            self.captured_message = message
            return ''

        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.input_func = patched_input_func
            command.handle(quiet=False)

        self.assertEquals(
            self.captured_message,
            'Do you want to delete existing data? Y/n: ')
        self.assertEquals(command.stdout.getvalue(), (
            'deleting existing content..'
            'creating localisations..'
            'creating categories..'
            'creating pages..'
            'done.'))

    def test_get_input_data_with_quiet_set(self):
        with self.settings(GIT_REPO_PATH=self.workspace.working_dir,
                           ELASTIC_GIT_INDEX_PREFIX=self.mk_index_prefix()):
            command = import_from_git.Command()
            command.stdout = StringIO()
            command.handle(quiet=True)
            self.assertEquals(command.stdout.getvalue(), '')

    @responses.activate
    def test_get_thumbor_image_file(self):
        host = 'http://localhost:8888'
        key = uuid.uuid4().hex
        command = import_from_git.Command()
        self.mock_get_image_response(host=host)

        file_obj, content_type = command.get_thumbor_image_file(
            host=host, uuid=key)
        self.assertIsInstance(file_obj, ContentFile)
        self.assertEqual(content_type, 'image/png')

        responses.reset()
        self.mock_get_image_response(host=host, status=404)

        file_obj, content_type = command.get_thumbor_image_file(
            host=host, uuid=key)
        self.assertIs(file_obj, None)
        self.assertIs(file_obj, None)

    @responses.activate
    def test_set_image_field(self):
        command = import_from_git.Command()
        command.stdout = StringIO()
        command.quiet = False
        command.disconnect_signals()

        host = 'http://localhost:8888'
        # 1 x 1 bitmap image
        body = 'BM:\x00\x00\x00\x00\x00\x00\x006\x00\x00\x00(\x00\x00\x00' \
               '\x01\x00\x00\x00\x01\x00\x00\x00\x01\x00\x18\x00\x00\x00' \
               '\x00\x00\x04\x00\x00\x00\x13\x0b\x00\x00\x13\x0b\x00\x00' \
               '\x00\x00\x00\x00\x00\x00\x00\x00\xff\xff\xff\x00'
        content_type = 'image/x-ms-bmp'
        self.mock_get_image_response(
            host=host, content_type=content_type, body=body)
        self.mock_get_on_redirect_image_response(
            host=host, content_type=content_type, body=body)
        self.mock_create_image_response(host=host)

        eg_obj = eg_models.Localisation({
            'locale': 'fra_FR',
            'image': uuid.uuid4().hex,
            'image_host': host})
        # set image dimensions to make sure we reassign them
        db_obj = Localisation.objects.create(
            language_code='fra', country_code='FR',
            image_width=5, image_height=5)

        # image exists and is on same server
        with self.settings(THUMBOR_SERVER=host):
            self.assertFalse(command.set_image_field(eg_obj, db_obj, 'image'))
        db_obj = Localisation.objects.get(
            language_code='fra', country_code='FR')
        self.assertEqual(command.stdout.getvalue(), '')
        self.assertTrue(
            re.match(r'/image/\w{32}/locales/image.bmp', db_obj.image.name))
        self.assertEqual(db_obj.image_width, 1)
        self.assertEqual(db_obj.image_height, 1)

        command.stdout = StringIO()
        db_obj.image = None
        db_obj.save()

        # image exists but it's on another server
        with self.settings(THUMBOR_SERVER='another-server.com'):
            self.assertTrue(command.set_image_field(eg_obj, db_obj, 'image'))
        self.assertEqual(command.stdout.getvalue(), '')
        self.assertTrue(
            re.match(r'/image/\w{32}/locales/image.bmp', db_obj.image.name))
        self.assertEqual(db_obj.image_width, 1)
        self.assertEqual(db_obj.image_height, 1)

        responses.reset()
        self.mock_get_image_response(host=host, status=404)
        command.stdout = StringIO()

        # image does not exist on server
        self.assertFalse(command.set_image_field(eg_obj, db_obj, 'image'))
        self.assertTrue(command.stdout.getvalue().startswith('WARNING: image'))

        # no image set in Git
        command.stdout = StringIO()
        self.assertFalse(command.set_image_field(eg_obj, db_obj, 'logo_image'))
        self.assertFalse(db_obj.logo_image)

        responses.reset()
        self.mock_get_image_response(host=host, content_type='.bmp')

        # check that mimetype/extension mixup gets handled
        with  \
                mock.patch.object(db_obj.image, 'save') as mock_save_image, \
                self.settings(THUMBOR_SERVER='another-server.com'):
            self.assertTrue(command.set_image_field(eg_obj, db_obj, 'image'))
            file_name = mock_save_image.call_args[0][0]
            self.assertTrue(file_name.endswith('.bmp'))

        command.reconnect_signals()
<|endoftext|>


<commit_before>from fractions import Fraction
from copy import deepcopy

ENV = {}

def scanner(input_str):
    '''Scans the input string from standard input and replaces '(' with ' [ '
        and ')' with ' ] ' '''
    split_tokens = []
    input_str = input_str.replace('(', ' ( ')
    input_str = input_str.replace(')', ' ) ')

    split_tokens = input_str.split()

    return split_tokens

def parser(un_parsed_list_of_tokens):
    '''sends each un parsed element from un parsed
        list of tokens and uses item_parser funtion to
        parse those items'''

    parsed_list_of_tokens = []

    def item_parser(x):
        '''parses individual items from un_parsed list of tokens'''
        try:
            int(x)
            return (int(x))
        except ValueError:
            return (x)

    def build_list(un_parsed_tokens):
        new_list = []
        x = 0

        if(un_parsed_tokens[x] == '('):
            x += 1

            while(x < len(un_parsed_tokens)):
                if(un_parsed_tokens[x] == ')'):
                    return new_list           # base Return
                elif(un_parsed_tokens[x] == '('):
                    respective_close_int = find_respective_close(un_parsed_tokens,x)
                    sub_list = build_list(un_parsed_tokens[x:respective_close_int + 1])
                    x  = respective_close_int + 1
                    new_list.append(sub_list)
                elif(un_parsed_tokens[x] != ')' or '('):
                    new_list.append(un_parsed_tokens[x])
                    x += 1
        return new_list

    for x in range(0,len(un_parsed_list_of_tokens)):
        parsed_list_of_tokens.append(item_parser(un_parsed_list_of_tokens[x]))
    return build_list(parsed_list_of_tokens)

def find_respective_close(token_list,open_index):
    open_p = 0
    close_p = 0
    for x in range(open_index,len(token_list)+1):
        if(token_list[x] == '('):
            open_p += 1
        elif(token_list[x] == ')'):
            close_p += 1
        if (open_p == close_p):
            return x

def eval_and_return(token, fn_env = None):
    if(type(token) is list):
        return evaluator(token)
    elif(type(token) is  str):
        try:
            return fn_env[token]
        except (KeyError, TypeError) as e:
            try:
                return ENV[token]
            except KeyError:
                print ("Variable not found")
#        else:
#            try:
#                return ENV[token]
#            except KeyError:
#                print ("Variable not found")

    elif(type(token) is int):
        return token

def arithmetic_operator(s_expression,fn_env = None):

    if(s_expression[0] == '+'):       # for expression starting with '+'
        result = 0
        x = 1

        while (x < len(s_expression)):

            s_expression[x] = eval_and_return(s_expression[x], fn_env)
            result += s_expression[x]
            x += 1

        return result

#    if(s_expression[0] == '+'):       # for expression starting with '+'
#        return reduce(lambda x,y : eval_and_return(x,fn_env) + eval_and_return(y,fn_env), s_expression[1:])  # testing fn_env
#
#    if(s_expression[0] == '-'):      # for expression starting with '-'
#        return reduce(lambda x,y : eval_and_return(x) - eval_and_return(y), s_expression[1:])
#
#    if(s_expression[0] == '*'):       # for expression starting with '*'
#        return reduce(lambda x,y : eval_and_return(x) * eval_and_return(y), s_expression[1:])
    if(s_expression[0] == '-'):      # for expression starting with '-'

        result = eval_and_return(s_expression[1])

        if(len(s_expression) == 2):   # Special case like (- 3) to return -3
            return (-1 * result)

        x = 2

        while (x < len(s_expression)):

            s_expression[x]  = eval_and_return(s_expression[x])
            result -= s_expression[x]
            x += 1

        return result

    if(s_expression[0] == '*'):       # for expression starting with '*'
        result = 1
        x = 1

        while (x < len(s_expression)):
            s_expression[x]  = eval_and_return(s_expression[x])
            result *= s_expression[x]
            x += 1

        return result

    if(s_expression[0] == '/'):       # for expression starting with '/'
        result = eval_and_return(s_expression[1])
        x = 2

        if(len(s_expression) == 2):     # special case to return (/ 5) as (1/5)
            return 1/s_expression[1]

        while (x < len(s_expression)):
            s_expression[x]  = eval_and_return(s_expression[x])
            result /= s_expression[x]
            x += 1

            return result

 #       return reduce(lambda x,y : eval_and_return(x) / eval_and_return(y), s_expression[1:])

def relational_operator(s_expression):
    ''' expects a list with first element with either '>' or '<' returns #t or
    #f based on the operands'''
    if(len(s_expression) == 2):
        return '#t'

    x = 2
    for y in range(0,len(s_expression)):
        if(type(s_expression[y]) == type([])):
            s_expression[y] = evaluator(s_expression[y])

    if(s_expression[0] == '<'):
        while x < len(s_expression):
            if ( s_expression[x-1] >= s_expression[x]):
                return '#f'
            x += 1
        return '#t'

    if(s_expression[0] == '>'):
        while x < len(s_expression):
            if (s_expression[x-1] <= s_expression[x]):
                return '#f'
            x += 1
        return '#t'

    if(s_expression[0] == '<='):
            while x < len(s_expression):
                if ( s_expression[x-1] > s_expression[x]):
                    return '#f'
                x += 1
            return '#t'

    if(s_expression[0] == '>='):
        while x < len(s_expression):
            if (s_expression[x-1] < s_expression[x]):
                return '#f'
            x += 1
        return '#t'

def bind_variable(s_expression):

    try:

        if(s_expression[2][0] == 'lambda'):

            ENV[s_expression[1]] = s_expression[2]
            return ENV
    except TypeError:
        pass

    ENV[s_expression[1]] = eval_and_return(s_expression[2])

    return ENV    # review needed to decide the return type

def if_statement(s_expression):
    if (evaluator(s_expression[1]) == '#t'):
        if(type(s_expression[2]) == type([])):
            return evaluator(s_expression[2])
        elif(type(s_expression[2]) == type(0)):
            return s_expression[2]
        elif(type(s_expression[2] == type(''))):
            try:
                return (ENV[s_expression[2]])
            except KeyError:
                print("variable not found")

    else:
        if(type(s_expression[3]) == type([])):
            return evaluator(s_expression[3])
        elif(type(s_expression[3]) == type(0)):
            return s_expression[3]
        elif(type(s_expression[3] == type(''))):
            try:
                return (ENV[s_expression[3]])
            except KeyError:
                print("variable not found")

def function_call(s_expression, lambda_expression):
    fn_env = {}
    if(len(s_expression[1:])  != len(lambda_expression[1])):
           raise SyntaxError ("number of actual args and formal args not matching")

    for x in range(0,len(lambda_expression[1])):  # building function_env
        fn_env[lambda_expression[1][x]] =  eval_and_return(s_expression [x+1])  # assigning s_expression's args to saved lambda's variables in function_env dict
#    return function_env   # return for testing purpose
#    global ENV
    if(fn_env == {}):
        fn_env = None
#    ENV = {**ENV , **function_env}              # workaround and needs to be changed
    print ("lambda expr :",lambda_expression[2],"fn_env",fn_env)
    return evaluator(lambda_expression[2],fn_env)

def evaluator(s_expression, fn_env = None):
    ''' gets a list as input and dispatches the list to various functions based on the first element of the list '''
    if (s_expression[0] == '+' or s_expression[0] ==  '-' or s_expression[0] ==  '*' or s_expression[0] ==  '/'):
        result = arithmetic_operator(s_expression, fn_env)
        return result
    elif(s_expression[0] == '>' or s_expression[0] == '<'  or s_expression[0] == '>=' or s_expression[0] == '<='):
        result = relational_operator(s_expression)
        return result

    elif (s_expression[0] == 'define'):
        bind_variable(s_expression) # review needed to decide what return to put
        return ENV
    elif (s_expression[0] == 'if'):
        return if_statement(s_expression)

    elif(s_expression[0] == 'begin'):

        for x in range(0,len(s_expression)):

            if(type(s_expression[x]) == type([])):
                result = evaluator(s_expression[x])
                if(x == (len(s_expression) - 1)):
                    return result

    elif(s_expression[0] == 'max'):
        result = max_fn(s_expression)
        return result

    elif(s_expression[0] == 'min'):
        result = min_fn(s_expression)
        return result

    elif(s_expression[0] == 'quote'):
        result = quote_fn(s_expression)
        return result

    elif(s_expression[0] in ENV):                   # user defined function call
        if type(ENV[s_expression[0]]) == list:
            if (ENV[s_expression[0]][0] == 'lambda'):
                lambda_expression =  deepcopy(ENV[s_expression[0]])  # point
                return function_call(s_expression,lambda_expression)

def max_fn(s_expression):
    for x in range(1,len(s_expression)):
        if type(s_expression[x]) == type([]):
            s_expression[x] =  evaluator(s_expression[x])
    return max(s_expression[1:])

def min_fn(s_expression):
    for x in range(1,len(s_expression)):
        if type(s_expression[x]) == type([]):
            s_expression[x] =  evaluator(s_expression[x])
    return min(s_expression[1:])

def quote_fn(s_expression):
    s_expression[1] = str(s_expression[1]).replace("[","(").replace("]",")").replace("'",'').replace(",",'')
    return s_expression[1]

def make_float_fraction(float_value):

    return str(Fraction(float_value).limit_denominator())

if __name__ == '__main__':

    while True:                  # REPL
        input_value = input("manoj's lispy >>> ")
        result = evaluator((parser(scanner(input_value))))
        if(isinstance(result,float)):
           result =  make_float_fraction(result)
        print ("LISPY output : ",result)
<commit_msg>refactored min and max function and arithmetic operator function<commit_after>from fractions import Fraction
from copy import deepcopy
from functools import reduce

ENV = {}

def scanner(input_str):
    '''Scans the input string from standard input and replaces '(' with ' [ '
        and ')' with ' ] ' '''
    split_tokens = []
    input_str = input_str.replace('(', ' ( ')
    input_str = input_str.replace(')', ' ) ')

    split_tokens = input_str.split()

    return split_tokens

def parser(un_parsed_list_of_tokens):
    '''sends each un parsed element from un parsed
        list of tokens and uses item_parser funtion to
        parse those items'''

    parsed_list_of_tokens = []

    def item_parser(x):
        '''parses individual items from un_parsed list of tokens'''
        try:
            int(x)
            return (int(x))
        except ValueError:
            return (x)

    def build_list(un_parsed_tokens):
        new_list = []
        x = 0

        if(un_parsed_tokens[x] == '('):
            x += 1

            while(x < len(un_parsed_tokens)):
                if(un_parsed_tokens[x] == ')'):
                    return new_list           # base Return
                elif(un_parsed_tokens[x] == '('):
                    respective_close_int = find_respective_close(un_parsed_tokens,x)
                    sub_list = build_list(un_parsed_tokens[x:respective_close_int + 1])
                    x  = respective_close_int + 1
                    new_list.append(sub_list)
                elif(un_parsed_tokens[x] != ')' or '('):
                    new_list.append(un_parsed_tokens[x])
                    x += 1
        return new_list

    for x in range(0,len(un_parsed_list_of_tokens)):
        parsed_list_of_tokens.append(item_parser(un_parsed_list_of_tokens[x]))
    return build_list(parsed_list_of_tokens)

def find_respective_close(token_list,open_index):
    open_p = 0
    close_p = 0
    for x in range(open_index,len(token_list)+1):
        if(token_list[x] == '('):
            open_p += 1
        elif(token_list[x] == ')'):
            close_p += 1
        if (open_p == close_p):
            return x

def eval_and_return(token, fn_env = None):
    if(type(token) is list):
        return evaluator(token)
    elif(type(token) is  str):
        try:
            return fn_env[token]
        except (KeyError, TypeError) as e:
            try:
                return ENV[token]
            except KeyError:
                print ("Variable not found")
#        else:
#            try:
#                return ENV[token]
#            except KeyError:
#                print ("Variable not found")

    elif(type(token) is int):
        return token
    elif(type(token) is float):
        return token

def arithmetic_operator(s_expression,fn_env = None):

    if(s_expression[0] == '+'):
        if (len(s_expression) == 2):
            return eval_and_return(s_expression[1])

        return reduce((lambda x,y : (eval_and_return(x,fn_env)) + (eval_and_return(y,fn_env))),s_expression[1:]) # testing fn_env

    if(s_expression[0] == '-'):

        if(len(s_expression) == 2):
            return (-1 * eval_and_return(s_expression[1]))

        return reduce((lambda x,y : (eval_and_return(x,fn_env)) - (eval_and_return(y,fn_env))),s_expression[1:]) # testing fn_env

    if(s_expression[0] == '*'):
        if(len(s_expression) == 2):
            return eval_and_return(s_expression[1])

        return reduce((lambda x, y : (eval_and_return(x, fn_env)) * (eval_and_return(y,fn_env))),s_expression[1:]) # testing fn_env

    if(s_expression[0] == '/'):

        if(len(s_expression) == 2):     # special case to return (/ 5) as (1/5)
            return 1/eval_and_return(s_expression[1])

        return reduce((lambda x,y : (eval_and_return(x,fn_env)) / (eval_and_return(y,fn_env))),s_expression[1:]) # testing fn_env

def relational_operator(s_expression):
    ''' expects a list with first element with either '>' or '<' returns #t or
    #f based on the operands'''
    if(len(s_expression) == 2):
        return '#t'

    x = 2
    for y in range(0,len(s_expression)):
        if(type(s_expression[y]) == type([])):
            s_expression[y] = evaluator(s_expression[y])

    if(s_expression[0] == '<'):
        while x < len(s_expression):
            if ( s_expression[x-1] >= s_expression[x]):
                return '#f'
            x += 1
        return '#t'

    if(s_expression[0] == '>'):
        while x < len(s_expression):
            if (s_expression[x-1] <= s_expression[x]):
                return '#f'
            x += 1
        return '#t'

    if(s_expression[0] == '<='):
            while x < len(s_expression):
                if ( s_expression[x-1] > s_expression[x]):
                    return '#f'
                x += 1
            return '#t'

    if(s_expression[0] == '>='):
        while x < len(s_expression):
            if (s_expression[x-1] < s_expression[x]):
                return '#f'
            x += 1
        return '#t'

def bind_variable(s_expression):

    try:

        if(s_expression[2][0] == 'lambda'):

            ENV[s_expression[1]] = s_expression[2]
            return ENV
    except TypeError:
        pass

    ENV[s_expression[1]] = eval_and_return(s_expression[2])

    return ENV    # review needed to decide the return type

def if_statement(s_expression):
    if (evaluator(s_expression[1]) == '#t'):
        if(type(s_expression[2]) == type([])):
            return evaluator(s_expression[2])
        elif(type(s_expression[2]) == type(0)):
            return s_expression[2]
        elif(type(s_expression[2] == type(''))):
            try:
                return (ENV[s_expression[2]])
            except KeyError:
                print("variable not found")

    else:
        if(type(s_expression[3]) == type([])):
            return evaluator(s_expression[3])
        elif(type(s_expression[3]) == type(0)):
            return s_expression[3]
        elif(type(s_expression[3] == type(''))):
            try:
                return (ENV[s_expression[3]])
            except KeyError:
                print("variable not found")

def function_call(s_expression, lambda_expression):
    fn_env = {}
    if(len(s_expression[1:])  != len(lambda_expression[1])):
           raise SyntaxError ("number of actual args and formal args not matching")

    for x in range(0,len(lambda_expression[1])):  # building function_env
        fn_env[lambda_expression[1][x]] =  eval_and_return(s_expression [x+1])  # assigning s_expression's args to saved lambda's variables in function_env dict
#    return function_env   # return for testing purpose
#    global ENV
    if(fn_env == {}):
        fn_env = None
#    ENV = {**ENV , **function_env}              # workaround and needs to be changed
    print ("lambda expr :",lambda_expression[2],"fn_env",fn_env)
    return evaluator(lambda_expression[2],fn_env)

def evaluator(s_expression, fn_env = None):
    ''' gets a list as input and dispatches the list to various functions based on the first element of the list '''
    if (s_expression[0] == '+' or s_expression[0] ==  '-' or s_expression[0] ==  '*' or s_expression[0] ==  '/'):
        result = arithmetic_operator(s_expression, fn_env)
        return result
    elif(s_expression[0] == '>' or s_expression[0] == '<'  or s_expression[0] == '>=' or s_expression[0] == '<='):
        result = relational_operator(s_expression)
        return result

    elif (s_expression[0] == 'define'):
        bind_variable(s_expression) # review needed to decide what return to put
        return ENV
    elif (s_expression[0] == 'if'):
        return if_statement(s_expression)

    elif(s_expression[0] == 'begin'):

        for x in range(0,len(s_expression)):

            if(type(s_expression[x]) == type([])):
                result = evaluator(s_expression[x])
                if(x == (len(s_expression) - 1)):
                    return result

    elif(s_expression[0] == 'max' or s_expression[0] == 'min'):
        result = max_min(s_expression, s_expression[0])
        return result

    elif(s_expression[0] == 'quote'):
        result = quote_fn(s_expression)
        return result

    elif(s_expression[0] in ENV):                   # user defined function call
        if type(ENV[s_expression[0]]) == list:
            if (ENV[s_expression[0]][0] == 'lambda'):
                lambda_expression =  deepcopy(ENV[s_expression[0]])  # point
                return function_call(s_expression,lambda_expression)

def max_min(s_expression, func=None):
    if(func == 'max'):
        return max(map(eval_and_return, s_expression[1:]))
    elif(func == 'min'):
        return min(map(eval_and_return, s_expression[1:]))

def quote_fn(s_expression):
    s_expression[1] = str(s_expression[1]).replace("[","(").replace("]",")").replace("'",'').replace(",",'')
    return s_expression[1]

def make_float_fraction(float_value):

    return str(Fraction(float_value).limit_denominator())

if __name__ == '__main__':

    while True:                  # REPL
        input_value = input("manoj's lispy >>> ")
        result = evaluator((parser(scanner(input_value))))
        if(isinstance(result,float)):
           result =  make_float_fraction(result)
        print ("LISPY output : ",result)
<|endoftext|>