Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Merge pull request #11 from mozilla-services/refactoring
Refactoring
- Loading branch information
Showing
28 changed files
with
756 additions
and
559 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,86 @@ | ||
from abc import ABCMeta, abstractmethod | ||
|
||
|
||
class Behavior(object): | ||
"""Registry for behaviors. | ||
A behavior is a class that implements two methods: | ||
- on_before_handle | ||
- on_after_handle | ||
""" | ||
__metaclass__ = ABCMeta | ||
_cache = {} | ||
|
||
@abstractmethod | ||
def on_before_handle(self, protocol, source, dest, to_backend): | ||
pass | ||
|
||
@abstractmethod | ||
def on_after_handle(self, protocol, source, dest, to_backend): | ||
pass | ||
|
||
@classmethod | ||
def __subclasshook__(cls, klass): | ||
if cls is Behavior: | ||
for method in cls.__abstractmethods__: | ||
if any(method in base.__dict__ for base in klass.__mro__): | ||
continue | ||
return NotImplemented | ||
return True | ||
return NotImplemented | ||
|
||
@classmethod | ||
def register(cls, subclass): | ||
ABCMeta.register(cls, subclass) | ||
if subclass not in cls._abc_registry: | ||
cls._abc_registry.add(subclass) | ||
|
||
@classmethod | ||
def _get_instance(cls, klass): | ||
name = klass.name | ||
if name not in cls._cache: | ||
cls._cache[name] = klass() | ||
return cls._cache[name] | ||
|
||
@classmethod | ||
def get_behaviors(cls): | ||
return dict([(klass.name, cls._get_instance(klass)) | ||
for klass in cls._abc_registry]) | ||
|
||
@classmethod | ||
def get_behavior(cls, name): | ||
for klass in cls._abc_registry: | ||
if klass.name == name: | ||
return cls._get_instance(klass) | ||
raise KeyError(name) | ||
|
||
|
||
def get_behaviors(): | ||
"""Return a mapping of all behaviors. | ||
The keys are the behavior names and the values the classes. | ||
""" | ||
return Behavior.get_behaviors() | ||
|
||
|
||
def get_behavior(name): | ||
"""Returns an instance of the given behavior.""" | ||
return Behavior.get_behaviors(name)() | ||
|
||
|
||
# manually register built-in behaviors | ||
from vaurien.behaviors.dummy import Dummy | ||
Behavior.register(Dummy) | ||
|
||
from vaurien.behaviors.error import Error | ||
Behavior.register(Error) | ||
|
||
from vaurien.behaviors.blackout import Blackout | ||
Behavior.register(Blackout) | ||
|
||
from vaurien.behaviors.delay import Delay | ||
Behavior.register(Delay) | ||
|
||
from vaurien.behaviors.hang import Hang | ||
Behavior.register(Hang) |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,16 @@ | ||
from vaurien.behaviors.dummy import Dummy | ||
|
||
|
||
class Blackout(Dummy): | ||
"""Reads the packets that have been sent then hangs. | ||
Acts like a *pdb.set_trace()* you'd forgot in your code ;) | ||
""" | ||
name = 'blackout' | ||
options = {} | ||
|
||
def on_before_handle(self, protocol, source, dest, to_backend): | ||
# consume the socket and hang | ||
source.close() | ||
source._closed = True | ||
return False |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,33 @@ | ||
import re | ||
|
||
|
||
class Dummy(object): | ||
"""Transparent behavior. Nothing's done. | ||
""" | ||
name = 'dummy' | ||
options = {} | ||
|
||
def __init__(self): | ||
self.settings = {} | ||
|
||
def update_settings(self, settings): | ||
self.settings.update(settings) | ||
|
||
def _convert(self, value, type_): | ||
if isinstance(value, type_): | ||
return value | ||
if type_ == bool: | ||
value = value.lower() | ||
return value in ('y', 'yes', '1', 'on') | ||
return type_(value) | ||
|
||
def option(self, name): | ||
type_, default = self.options[name][1:3] | ||
value = self.settings.get(name, default) | ||
return self._convert(value, type_) | ||
|
||
def on_before_handle(self, protocol, source, dest, to_backend): | ||
return True | ||
|
||
def on_after_handle(self, protocol, source, dest, to_backend): | ||
return True |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -1,20 +1,22 @@ | ||
import gevent | ||
from vaurien.handlers.base import BaseHandler | ||
|
||
from vaurien.behaviors.dummy import Dummy | ||
from vaurien.util import get_data | ||
|
||
class Hang(BaseHandler): | ||
|
||
class Hang(Dummy): | ||
"""Reads the packets that have been sent then hangs. | ||
Acts like a *pdb.set_trace()* you'd forgot in your code ;) | ||
""" | ||
name = 'hang' | ||
options = {} | ||
|
||
def ___call__(self, source, dest, to_backend): | ||
def on_before_handle(self, protocol, source, dest, to_backend): | ||
# consume the socket and hang | ||
data = self._get_data(source, dest, to_backend) | ||
data = get_data(source) | ||
while data: | ||
data = self._get_data(source, dest, to_backend) | ||
data = get_data(source) | ||
|
||
while True: | ||
gevent.sleep(1.) |
Oops, something went wrong.