# This file is part of Buildbot.  Buildbot is free software: you can
# redistribute it and/or modify it under the terms of the GNU General Public
# License as published by the Free Software Foundation, version 2.
#
# This program is distributed in the hope that it will be useful, but WITHOUT
# ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
# FOR A PARTICULAR PURPOSE.  See the GNU General Public License for more
# details.
#
# You should have received a copy of the GNU General Public License along with
# this program; if not, write to the Free Software Foundation, Inc., 51
# Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
#
# Copyright Buildbot Team Members

from __future__ import with_statement


from collections import deque
import os
import cPickle as pickle

from zope.interface import implements, Interface


def ReadFile(path):
    with open(path, 'rb') as f:
        return f.read()


def WriteFile(path, buf):
    with open(path, 'wb') as f:
        f.write(buf)


class IQueue(Interface):
    """Abstraction of a queue."""
    def pushItem(item):
        """Adds an individual item to the end of the queue.

        Returns an item if it was overflowed."""

    def insertBackChunk(items):
        """Adds a list of items as the oldest entries.

        Normally called in case of failure to process the data, queue the data
        back so it can be retrieved at a later time.

        Returns a list of items if it was overflowed."""

    def popChunk(nbItems=None):
        """Pop many items at once. Defaults to self.maxItems()."""

    def save():
        """Save the queue to storage if implemented."""

    def items():
        """Returns items in the queue.

        Warning: Can be extremely slow for queue on disk."""

    def nbItems():
        """Returns the number of items in the queue."""

    def maxItems():
        """Returns the maximum number of items this queue can hold."""


class MemoryQueue(object):
    """Simple length bounded queue using deque.

    list.pop(0) operation is O(n) so for a 10000 items list, it can start to
    be real slow. On the contrary, deque.popleft() is O(1) most of the time.
    See http://docs.python.org/library/collections.html for more
    information.
    """
    implements(IQueue)

    def __init__(self, maxItems=None):
        self._maxItems = maxItems
        if self._maxItems is None:
            self._maxItems = 10000
        self._items = deque()

    def pushItem(self, item):
        ret = None
        if len(self._items) == self._maxItems:
            ret = self._items.popleft()