summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--factory/base.py148
1 files changed, 72 insertions, 76 deletions
diff --git a/factory/base.py b/factory/base.py
index 2418675..17bd267 100644
--- a/factory/base.py
+++ b/factory/base.py
@@ -290,6 +290,68 @@ class BaseFactory(object):
return getattr(cls, CLASS_ATTRIBUTE_DECLARATIONS).copy(extra_defs)
@classmethod
+ def _adjust_kwargs(cls, **kwargs):
+ """Extension point for custom kwargs adjustment."""
+ return kwargs
+
+ @classmethod
+ def _prepare(cls, create, **kwargs):
+ """Prepare an object for this factory.
+
+ Args:
+ create: bool, whether to create or to build the object
+ **kwargs: arguments to pass to the creation function
+ """
+ target_class = getattr(cls, CLASS_ATTRIBUTE_ASSOCIATED_CLASS)
+ kwargs = cls._adjust_kwargs(**kwargs)
+
+ # Extract *args from **kwargs
+ args = tuple(kwargs.pop(key) for key in cls.FACTORY_ARG_PARAMETERS)
+
+ if create:
+ return cls._create(target_class, *args, **kwargs)
+ else:
+ return cls._build(target_class, *args, **kwargs)
+
+ @classmethod
+ def _generate(cls, create, attrs):
+ """generate the object.
+
+ Args:
+ create (bool): whether to 'build' or 'create' the object
+ attrs (dict): attributes to use for generating the object
+ """
+ # Extract declarations used for post-generation
+ postgen_declarations = getattr(cls, CLASS_ATTRIBUTE_POSTGEN_DECLARATIONS)
+ postgen_attributes = {}
+ for name, decl in sorted(postgen_declarations.items()):
+ postgen_attributes[name] = decl.extract(name, attrs)
+
+ # Generate the object
+ obj = cls._prepare(create, **attrs)
+
+ # Handle post-generation attributes
+ results = {}
+ for name, decl in sorted(postgen_declarations.items()):
+ extracted, extracted_kwargs = postgen_attributes[name]
+ results[name] = decl.call(obj, create, extracted, **extracted_kwargs)
+
+ cls._after_postgeneration(obj, create, results)
+
+ return obj
+
+ @classmethod
+ def _after_postgeneration(cls, obj, create, results=None):
+ """Hook called after post-generation declarations have been handled.
+
+ Args:
+ obj (object): the generated object
+ create (bool): whether the strategy was 'build' or 'create'
+ results (dict or None): result of post-generation declarations
+ """
+ pass
+
+ @classmethod
def _build(cls, target_class, *args, **kwargs):
"""Actually build an instance of the target_class.
@@ -322,7 +384,8 @@ class BaseFactory(object):
@classmethod
def build(cls, **kwargs):
"""Build an instance of the associated class, with overriden attrs."""
- raise cls.UnsupportedStrategy()
+ attrs = cls.attributes(create=False, extra=kwargs)
+ return cls._generate(False, attrs)
@classmethod
def build_batch(cls, size, **kwargs):
@@ -339,7 +402,8 @@ class BaseFactory(object):
@classmethod
def create(cls, **kwargs):
"""Create an instance of the associated class, with overriden attrs."""
- raise cls.UnsupportedStrategy()
+ attrs = cls.attributes(create=True, extra=kwargs)
+ return cls._generate(True, attrs)
@classmethod
def create_batch(cls, size, **kwargs):
@@ -455,90 +519,22 @@ class Factory(BaseFactory):
ABSTRACT_FACTORY = True
FACTORY_STRATEGY = CREATE_STRATEGY
- @classmethod
- def _adjust_kwargs(cls, **kwargs):
- """Extension point for custom kwargs adjustment."""
- return kwargs
- @classmethod
- def _prepare(cls, create, **kwargs):
- """Prepare an object for this factory.
-
- Args:
- create: bool, whether to create or to build the object
- **kwargs: arguments to pass to the creation function
- """
- target_class = getattr(cls, CLASS_ATTRIBUTE_ASSOCIATED_CLASS)
- kwargs = cls._adjust_kwargs(**kwargs)
-
- # Extract *args from **kwargs
- args = tuple(kwargs.pop(key) for key in cls.FACTORY_ARG_PARAMETERS)
-
- if create:
- return cls._create(target_class, *args, **kwargs)
- else:
- return cls._build(target_class, *args, **kwargs)
-
- @classmethod
- def _generate(cls, create, attrs):
- """generate the object.
-
- Args:
- create (bool): whether to 'build' or 'create' the object
- attrs (dict): attributes to use for generating the object
- """
- # Extract declarations used for post-generation
- postgen_declarations = getattr(cls, CLASS_ATTRIBUTE_POSTGEN_DECLARATIONS)
- postgen_attributes = {}
- for name, decl in sorted(postgen_declarations.items()):
- postgen_attributes[name] = decl.extract(name, attrs)
-
- # Generate the object
- obj = cls._prepare(create, **attrs)
-
- # Handle post-generation attributes
- results = {}
- for name, decl in sorted(postgen_declarations.items()):
- extracted, extracted_kwargs = postgen_attributes[name]
- results[name] = decl.call(obj, create, extracted, **extracted_kwargs)
-
- cls._after_postgeneration(obj, create, results)
+Factory.AssociatedClassError = AssociatedClassError
- return obj
- @classmethod
- def _after_postgeneration(cls, obj, create, results=None):
- """Hook called after post-generation declarations have been handled.
+class StubFactory(Factory):
- Args:
- obj (object): the generated object
- create (bool): whether the strategy was 'build' or 'create'
- results (dict or None): result of post-generation declarations
- """
- pass
+ FACTORY_STRATEGY = STUB_STRATEGY
+ FACTORY_FOR = containers.StubObject
@classmethod
def build(cls, **kwargs):
- attrs = cls.attributes(create=False, extra=kwargs)
- return cls._generate(False, attrs)
+ raise UnsupportedStrategy()
@classmethod
def create(cls, **kwargs):
- attrs = cls.attributes(create=True, extra=kwargs)
- return cls._generate(True, attrs)
-
-
-Factory.AssociatedClassError = AssociatedClassError
-
-
-class StubFactory(BaseFactory):
- __metaclass__ = FactoryMetaClass
-
- FACTORY_STRATEGY = STUB_STRATEGY
-
- FACTORY_FOR = containers.StubObject
-
-print StubFactory._associated_class
+ raise UnsupportedStrategy()
class DjangoModelFactory(Factory):