标签: factory-boy

如何使用Factory_Boy创建管理员用户?

我是Django的初学者,刚开始为我的项目做一些测试.我想要做的是用selenium构建一个功能测试,登录到Django Admin站点.

我首先按照本教程http://www.tdd-django-tutorial.com/tutorial/1/使用fixtures和dumpdata来为测试应用程序(创建新数据库)提供管理员帐户信息.这很好用.

然后我想看看我是否可以使用工厂男孩来替换灯具.工厂男孩通过在tests.py文件中实例化必要的对象来工作,这对我来说似乎更干净.不知怎的,我无法让这个工作,Factory_boy文档不太有用......

这是我的tests.py

from django.test import LiveServerTestCase
from django.contrib.auth.models import User
from selenium import webdriver
from selenium.webdriver.common.keys import Keys
import factory

class UserFactory(factory.Factory):
    FACTORY_FOR = User

    username = 'jeff'
    password = 'pass'
    is_superuser = True

class AdminTest(LiveServerTestCase):

    def setUp(self):
        self.browser = webdriver.Firefox()

    def tearDown(self):
        self.browser.quit()

    def test_if_admin_login_is_possible(self):
        jeff = UserFactory.create()

        # Jeff opens the browser and goes to the admin page
        self.browser = webdriver.Firefox()
        self.browser.get(self.live_server_url + '/admin/')

        # Jeff sees the familiar 'Django Administration' …
Run Code Online (Sandbox Code Playgroud)

python django selenium factory-boy

23
推荐指数
5
解决办法
6149
查看次数

如何使用Factory_boy中的Faker

Factory_boy用于fake-factory (Faker)生成随机值,我想直接使用Faker在我的Django测试中生成一些随机值.

Factory_boy文档建议使用factory.Faker及其提供者:

class RandomUserFactory(factory.Factory):
    class Meta:
        model = models.User

    first_name = factory.Faker('first_name')
Run Code Online (Sandbox Code Playgroud)

但这不会产生任何名称:

>>> import factory
>>> factory.Faker('name')
<factory.faker.Faker object at 0x7f1807bf5278>
>>> type(factory.Faker('name'))
<class 'factory.faker.Faker'>
Run Code Online (Sandbox Code Playgroud)

factory_boy faker.pyfactory.Faker('ean', length=10)调用,faker.Faker.ean(length=10)Faker文档说它应该显示一个名称:

from faker import Faker
fake = Faker()
fake.name()
# 'Lucy Cechtelar'
Run Code Online (Sandbox Code Playgroud)

有没有其他方法可以使用Faker而不是直接设置实例Faker

from faker import Factory
fake = Factory.create()
fake.name()
Run Code Online (Sandbox Code Playgroud)

python factory django-testing faker factory-boy

17
推荐指数
3
解决办法
5567
查看次数

避免与factory_boy工厂重复

我正在使用factory_boy来创建测试夹具.我有两个简单的工厂,由SQLAlchemy模型支持(简化如下).

我希望能够AddressFactory.create()多次调用,并且Country如果它还不存在则创建它,否则我希望它重新使用现有记录.

class CountryFactory(factory.Factory):
    FACTORY_FOR = Country

    cc = "US"
    name = "United States"


class AddressFactory(factory.Factory):
    FACTORY_FOR = Address

    name = "Joe User"
    city = "Seven Mile Beach"
    country = factory.SubFactory(CountryFactory, cc="KY", name="Cayman Islands")
Run Code Online (Sandbox Code Playgroud)

我的问题是:如何设置这些工厂,以便factory_boy每次创建地址时都不会尝试创建新的国家/地区?

python sqlalchemy factory-boy

15
推荐指数
1
解决办法
3417
查看次数

Django-工厂男孩在一家工厂没有明显原因失败

代码:类StockFactory(UniqueObjectsFactory):FACTORY_FOR =股票FACTORY_DJANGO_GET_OR_CREATE =('name','market')

market = factory.SubFactory(MarketFactory)
symbol = FuzzyAttribute(lambda: ''.join(random.choice(string.ascii_uppercase) for _ in xrange(4)))
name = FuzzyCompanyName()
# last_trade_price = fuzzy.FuzzyDecimal(0.0, 10000.0)


class PositionsFactory(FreezeableFactory):
    FACTORY_FOR = Position
    FACTORY_DJANGO_GET_OR_CREATE = ('stock','AnotherObject')

    id = FuzzyInteger(100000)
    stock = factory.SubFactory(Stock)

    AnotherObject = factory.SubFactory(AnotherObject)  #If I comment stock out it would fail here

    created_date = FuzzyDateTime(start_dt=datetime(2013, 1, 1, tzinfo=compat.UTC))
Run Code Online (Sandbox Code Playgroud)

错误:

 File "/home/alon/Projects/stox-server/execution/tests/functional/test_positions.py", line 21, in setUp
    PositionsFactory.create( portfolio=self.portfolio)
  File "/home/alon/.virtualenvs/stox-server/local/lib/python2.7/site-packages/factory/base.py", line 522, in create
    attrs = cls.attributes(create=True, extra=kwargs)
  File "/home/alon/.virtualenvs/stox-server/local/lib/python2.7/site-packages/factory/base.py", line 365, in attributes
    force_sequence=force_sequence, …
Run Code Online (Sandbox Code Playgroud)

django django-testing factory-boy

14
推荐指数
1
解决办法
1606
查看次数

django工厂男孩工厂与OneToOne的关系及相关领域

我正在使用Factory Boy为我的django应用程序创建测试工厂.我遇到问题的模型是一个非常基本的Account模型,它与django User auth模型有一个OneToOne关系(使用django <1.5):

# models.py
from django.contrib.auth.models import User
from django.db import models

class Account(models.Model):
    user = models.OneToOneField(User)
    currency = models.CharField(max_length=3, default='USD')
    balance = models.CharField(max_length="5", default='0.00') 
Run Code Online (Sandbox Code Playgroud)

这是我的工厂:

# factories.py
from django.db.models.signals import post_save
from django.contrib.auth.models import User

import factory

from models import Account


class AccountFactory(factory.django.DjangoModelFactory):
    FACTORY_FOR = Account

    user = factory.SubFactory('app.factories.UserFactory')
    currency             = 'USD'
    balance              = '50.00'

class UserFactory(factory.django.DjangoModelFactory):
    FACTORY_FOR = User

    username = 'bob'
    account = factory.RelatedFactory(AccountFactory)
Run Code Online (Sandbox Code Playgroud)

因此,每当调用AccountFactory时,我都希望工厂男孩能够创建一个相关的UserFactory:

# tests.py 
from django.test import TestCase

from …
Run Code Online (Sandbox Code Playgroud)

python testing django factory-boy

13
推荐指数
1
解决办法
4433
查看次数

为什么factory_boy优于在测试中直接使用ORM?

我不明白为什么factory_boy比直接在Django测试中创建ORM /模型实例更受欢迎.factory_boy网站几乎无法解释使用它的好处.

作为固定装置的替代品是有意义的,这些固定装置难以管理,速度慢等.

但是,为什么不只是根据测试需要创建模型实例?

如果factory_boy完全取代了对db的写入,那么很好,我认为在这种情况下它会非常有用,但工厂男孩创建的django模型实例仍然与数据库交互.

另一个潜在的好处是对序列的支持,但是在不需要工厂男孩的情况下创建序列/样本数据并不困难.

总而言之,我看到使用工厂男孩几乎没有任何好处,直接创建对象/模型实例.

我希望我错过了一些明显的东西!

python testing django unit-testing factory-boy

13
推荐指数
1
解决办法
2191
查看次数

factory_boy中的多对多关系?

我正在尝试使用factory_boy测试两个Django模型之间的多对多关系.factory_boy文档似乎没有讨论这个问题,我无法弄清楚我做错了什么.当我运行第一个测试时,我得到错误"AttributeError:'Pizza'对象没有属性'顶部'".第二次测试我得到了类似的错误.

当我在调试器中运行测试时,我可以看到"浇头"对象,但它不知道如何从中获取名称.我是否正确定义了PizzaFactory的_prepare方法?当你有多对多的关系时,如何从另一个表中访问一个表中的名称?

谢谢.

models.py:

from django.db import models

class Topping(models.Model):
    name = models.CharField(max_length=50)

    def __unicode__(self):
        return self.name

class Pizza(models.Model):
    name = models.CharField(max_length=100)
    toppings = models.ManyToManyField(Topping)

    def __unicode__(self):
        return self.name
Run Code Online (Sandbox Code Playgroud)

factories.py:

import factory
from models import Topping, Pizza

class ToppingFactory(factory.Factory):
    name = 'mushrooms'

class PizzaFactory(factory.Factory):
    name = 'Vegetarian'

    @classmethod
    def _prepare(cls, create, **kwargs):
        topping = ToppingFactory()
        pizza = super(PizzaFactory, cls)._prepare(create, **kwargs)
        pizza.toppings.add(topping)
        return pizza
Run Code Online (Sandbox Code Playgroud)

tests.py

from django.test import TestCase
import factory
from app.models import Topping, Pizza
from app.factories import ToppingFactory, PizzaFactory …
Run Code Online (Sandbox Code Playgroud)

unit-testing django-testing factory-boy

11
推荐指数
2
解决办法
6415
查看次数

将使用SubFactory和LazyAttribute创建的对象传递给factory_boy中的RelatedFactory

factory.LazyAttributeSubFactory调用中使用传入一个对象,在对象中创建factory_parent.这很好用.

但是,如果我将创建的对象传递给a RelatedFactory,LazyAttribute则无法再看到factory_parent并失败.

这很好用:

class OKFactory(factory.DjangoModelFactory):
    class = Meta:
        model = Foo
        exclude = ['sub_object']

    sub_object = factory.SubFactory(SubObjectFactory)

    object = factory.SubFactory(ObjectFactory,
        sub_object=factory.LazyAttribute(lambda obj: obj.factory_parent.sub_object))
Run Code Online (Sandbox Code Playgroud)

同样的呼叫在LazyAttribute这里失败:

class ProblemFactory(OKFactory):
    class = Meta:
        model = Foo
        exclude = ['sub_object', 'object']

    sub_object = factory.SubFactory(SubObjectFactory)

    object = factory.SubFactory(ObjectFactory,
        sub_object=factory.LazyAttribute(lambda obj: obj.factory_parent.sub_object))

    another_object = factory.RelatedFactory(AnotherObjectFactory, 'foo', object=object)
Run Code Online (Sandbox Code Playgroud)

相同的LazyAttribute调用不能再看到factory_parent,并且只能访问AnotherObject值.LazyAttribute抛出错误:

AttributeError: The parameter sub_object is unknown. Evaluated attributes are...[then lists all …
Run Code Online (Sandbox Code Playgroud)

python django associated-object factory-boy

10
推荐指数
2
解决办法
3529
查看次数

Django在夹具拆卸中测试IntegrityError

我开始使用这个factory_boy包,所以我建立了一些工厂,并想测试创建的对象不会引发任何验证错误。

这是我正在使用的 mixin,它基本上从一个模块中获取每个工厂,创建一个实例,然后测试从.full_clean(). 加载的用户设备是 ID 为 1 到 10 的 10 个实例。

class FactoriesTestCaseMixin:
    fixtures = [
        'user/tests/fixtures/user.json',
    ]
    module = None

    def test_factories(self):
        err_msg = '{name} caused errors:\n{errors}'
        factories = [
            (name, obj) for name, obj in inspect.getmembers(self.module, inspect.isclass)
            if obj.__module__ == self.module.__name__
            and not obj._meta.abstract
        ]
        for factory in factories:
            name = factory[0]
            instance = factory[1]()

            errors = None
            try:
                instance.full_clean()
            except ValidationError as e:
                errors = e

            self.assertTrue(errors is None, err_msg.format(name=name, errors=errors))
Run Code Online (Sandbox Code Playgroud)

mixin …

python django factory-boy

10
推荐指数
1
解决办法
457
查看次数

使用外键创建多个对象

我需要创建十个示例用户(User),每个用户必须有五十个文档(Doc).如何使用factoryboy在tests.py中执行此操作?

#factories.py

from app_name.models import *
import factory
from datetime import datetime, timedelta, time
from django.contrib.auth.models import User


class UserFactory(factory.Factory):
    FACTORY_FOR = User

    username = factory.Sequence(lambda n: 'User ' + n)
    email = 'demo@mail.com'
    password = '1234567'

class DocFactory(factory.Factory):
    FACTORY_FOR = Doc

    user = factory.SubFactory(UserFactory)
    kategories = '1'
    doc_number = '12345678'
    date_join = factory.Sequence(lambda n:(datetime.now() + timedelta(days=n)).date(), int)
Run Code Online (Sandbox Code Playgroud)

在我的tests.py中:

from django.test import TestCase
from django_dynamic_fixture import G
from factories import *
Run Code Online (Sandbox Code Playgroud)

python django factory-boy

9
推荐指数
2
解决办法
4911
查看次数