def test__eq__(self):
     """A `CommonName` is equal to another if relevant columns match."""
     cn1 = CommonName()
     cn2 = CommonName()
     idx = Index()
     idx.id = 1
     x = CommonName()
     y = CommonName()
     z = CommonName()
     x.id = 24
     y.id = 25
     z.id = 26
     cv1, cv2, cv3 = Cultivar(), Cultivar(), Cultivar()
     cn1.id = 42
     cn1.index = idx
     cn1.name = 'Annual'
     cn1.slug = 'annual'
     cn1.description = 'Not built to last.'
     cn1.instructions = 'Plant them.'
     cn1.gw_common_names = [x, y, z]
     cn1.gw_cultivars = [cv1, cv2, cv3]
     cn1.visible = True
     assert cn1 != cn2
     cn2.id = 42
     cn2.index = idx
     cn2.name = 'Annual'
     cn2.slug = 'annual'
     cn2.description = 'Not built to last.'
     cn2.instructions = 'Plant them.'
     cn2.gw_common_names = [x, y, z]
     cn2.gw_cultivars = [cv1, cv2, cv3]
     cn2.visible = True
     assert cn1 == cn2
 def test_cultivar_bad_slugs(self, app, db):
     """Return 404 if any slug given does not correspond to a db entry."""
     app.config["SHOW_CULTIVAR_PAGES"] = True
     idx = Index()
     cn = CommonName()
     cultivar = Cultivar()
     db.session.add_all([idx, cn, cultivar])
     idx.name = "Perennial Flower"
     cn.name = "Foxglove"
     cultivar.name = "Foxy"
     cultivar.common_name = cn
     cultivar.description = "Like that Hendrix song."
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug=idx.slug, cn_slug=cn.slug, cv_slug="no-biscuit"))
     assert rv.status_code == 404
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug="no_biscuit", cn_slug=cn.slug, cv_slug=cultivar.slug))
     assert rv.status_code == 404
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug=idx.slug, cn_slug="no-biscuit", cv_slug=cultivar.slug))
     assert rv.status_code == 404
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug="no-biscuit", cn_slug="no-biscuit", cv_slug="no-biscuit"))
     assert rv.status_code == 404
 def test_add_cultivar_successful_submit_no_stock_and_inactive(self, mock_save, app, db):
     """Flash messages if cultivar is not in stock and has been dropped."""
     bn = BotanicalName()
     cn = CommonName()
     idx = Index()
     db.session.add_all([bn, cn, idx])
     bn.name = "Digitalis purpurea"
     idx.name = "Perennial Flower"
     cn.name = "Foxglove"
     cn.index = idx
     bn.common_names.append(cn)
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.post(
             url_for("seeds.add_cultivar", cn_id=cn.id),
             data=dict(
                 botanical_name=str(bn.id),
                 index=str(idx.id),
                 description="Very foxy.",
                 active="",
                 in_stock="",
                 name="Foxy",
                 section="0",
                 thumbnail=(io.BytesIO(b"fawks"), "foxy.jpg"),
             ),
             follow_redirects=True,
         )
     assert '"Foxy Foxglove" is not in stock' in str(rv.data)
     assert '"Foxy Foxglove" is currently inactive' in str(rv.data)
 def test_edit_index_renders_page(self, app, db):
     """Render the page for editing a index given valid idx_id."""
     idx = Index()
     db.session.add(idx)
     idx.name = "Vegetable"
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.edit_index", idx_id=idx.id), follow_redirects=True)
     assert "Edit Index" in str(rv.data)
 def test_index_with_valid_slug(self, app, db):
     """Return valid page given a valid index slug."""
     idx = Index()
     db.session.add(idx)
     idx.name = "Annual Flower"
     idx.description = "Not really built to last."
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.index", idx_slug=idx.slug), follow_redirects=True)
     assert "Annual Flower" in str(rv.data)
 def test_select_index_success(self, app, db):
     """Redirect to dest with idx_id selected by form."""
     idx = Index()
     db.session.add(idx)
     idx.name = "Annual Flower"
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.post(url_for("seeds.select_index", dest="seeds.edit_index"), data=dict(index=idx.id))
     assert rv.status_code == 302
     assert rv.location == url_for("seeds.edit_index", idx_id=idx.id, _external=True)
 def test_auto_position_first(self, m_gai):
     """Set position to 1 if no other instances exist."""
     m_gai.return_value = []
     p1 = Index()
     # Since Index is not a declarative model, but a mixin that
     # adds a column to models, p1.position needs to be set to None before
     # using auto_position to prevent a TypeError from being raised due to
     # attempting to interpret an unbound column as a boolean.
     p1.position = None
     p1.auto_position()
     assert p1.position == 1
 def test_common_name_bad_slugs(self, app, db):
     """Give a 404 page if given malformed cn_slug and idx_slug."""
     cn = CommonName()
     idx = Index()
     db.session.add_all([cn, idx])
     cn.name = "Foxglove"
     idx.name = "Perennial Flower"
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.common_name", idx_slug="pewennial-flower", cn_slug="fawksglove"))
     assert rv.status_code == 404
 def test_auto_position_with_others(self, m_gai):
     p1 = Index()
     p1.position = 1
     p2 = Index()
     p2.position = 2
     p3 = Index()
     p3.position = 3
     m_gai.return_value = [p1, p2, p3]
     p4 = Index()
     p4.position = None
     p4.auto_position()
     assert p4.position == 4
 def test_common_name_renders_page(self, app, db):
     """Render page with common name info given valid slugs."""
     cn = CommonName()
     idx = Index()
     db.session.add_all([cn, idx])
     cn.name = "Foxglove"
     cn.description = "Do foxes really wear these?"
     idx.name = "Perennial Flower"
     cn.index = idx
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.common_name", idx_slug=idx.slug, cn_slug=cn.slug))
     assert "Do foxes really wear these?" in str(rv.data)
Example #11
0
 def test_from_dict__index_exists(self, m_q):
     """Do not allow from_dict_ to create an Index w/ id already in use."""
     old_idx = Index()
     old_idx.id = 42
     m_q.get.return_value = old_idx
     idx = Index()
     idx.id = 42
     idx.position = 3
     idx.name = 'Annual'
     idx.slug = 'annual'
     idx.description = 'Not built to last.'
     d = idx.dict_
     with pytest.raises(ValueError):
         Index.from_dict_(d)
def foxy_cultivar():
    """Generate a Cultivar object based on Foxy Foxglove."""
    cultivar = Cultivar()
    cultivar.name = "Foxy"
    cultivar.description = "Not to be confused with that Hendrix song."
    bn = BotanicalName()
    bn.name = "Digitalis purpurea"
    cultivar.botanical_name = bn
    idx = Index()
    idx.name = "Perennial Flower"
    cn = CommonName()
    cn.name = "Foxglove"
    cn.index = idx
    cultivar.common_name = cn
    return cultivar
Example #13
0
 def test_clean_positions_sets_nulls(self, m_pi):
     """Set positions for objects with no position set."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p4 = Index()
     p1.position = 1
     p2.position = None
     p3.position = 2
     p4.position = None
     m_pi.return_value = [p1, p2, p3, p4]
     p1.clean_positions()
     assert p1.position == 1
     assert p3.position == 2
     assert p2.position == 3
     assert p4.position == 4
Example #14
0
 def test_set_position_insert_first(self, m_pi):
     """Bump others up when inserting to start position."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 2
     p3.position = 3
     m_pi.return_value = [p1, p2, p3]
     ptest = Index()
     ptest.position = None
     ptest.set_position(1)
     assert ptest.position == 1
     assert p1.position == 2
     assert p2.position == 3
     assert p3.position == 4
Example #15
0
 def test_set_position_inserts(self, m_pi):
     """Setting a position btwn first and last should insert there."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 2
     p3.position = 3
     m_pi.return_value = [p1, p2, p3]
     ptest = Index()
     ptest.position = None
     ptest.set_position(2)
     assert p1.position == 1
     assert ptest.position == 2
     assert p2.position == 3
     assert p3.position == 4
 def test_remove_index_verified(self, app, db):
     """Remove Index from db if verify_removal is checked."""
     idx = Index()
     idx2 = Index()
     db.session.add_all([idx, idx2])
     idx.name = "Annual Flower"
     idx2.name = "Herb"
     db.session.commit()
     assert idx in Index.query.all()
     with app.test_client() as tc:
         tc.post(
             url_for("seeds.remove_index", idx_id=idx.id),
             data=dict(verify_removal=True, move_to=idx2.id),
             follow_redirects=True,
         )
     assert idx not in Index.query.all()
 def test_get_or_create_get(self, db):
     """Load Index if it exists."""
     idx = Index(name='Finger')
     db.session.add(idx)
     db.session.commit()
     assert Index.get_or_create(name='Finger') is idx
     assert not idx.created
Example #18
0
 def test_set_position_insert_after_last(self, m_pi):
     """Insert after last position if given arbitrarily larger position."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 2
     p3.position = 3
     m_pi.return_value = [p1, p2, p3]
     ptest = Index()
     ptest.position = None
     ptest.set_position(42)
     assert p1.position == 1
     assert p2.position == 2
     assert p3.position == 3
     assert ptest.position == 4
 def test__step_backward(self, db):
     """Get the previous instance in the sequence."""
     idx1 = Index()
     idx2 = Index()
     idx3 = Index()
     idx1.position = 1
     idx2.position = 3
     idx3.position = 4
     db.session.add_all([idx1, idx2, idx3])
     db.session.commit()
     assert idx3._step(forward=False) is idx2
     assert idx2._step(forward=False) is idx1
     assert idx1._step(forward=False) is None
 def test_remove_index_not_verified(self, app, db):
     """Redirect to self if verify_removal not checked."""
     idx = Index()
     idx2 = Index()
     db.session.add_all([idx, idx2])
     idx.name = "Annual Flower"
     idx2.name = "Herb"
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.post(url_for("seeds.remove_index", idx_id=idx.id), data=dict(verify_removal="", move_to=idx2.id))
     assert rv.location == url_for("seeds.remove_index", idx_id=idx.id, _external=True)
     with app.test_client() as tc:
         rv = tc.post(
             url_for("seeds.remove_index", idx_id=idx.id),
             data=dict(verify_removal="", move_to=idx2.id),
             follow_redirects=True,
         )
     assert "Index was not removed" in str(rv.data)
Example #21
0
 def test_dict__to_from_dict_existing_cn(self, m_q):
     """Do not create `CommonName` if id already exists in db."""
     old_cn = CommonName()
     old_cn.id = 42
     m_q.get.return_value = old_cn
     cn = CommonName()
     idx = Index()
     idx.id = 1
     cn.id = 42
     cn.index = idx
     cn.name = 'Annual'
     cn.slug = 'annual'
     cn.description = 'Not built to last.'
     cn.instructions = 'Plant them.'
     cn.visible = True
     d = cn.dict_
     with pytest.raises(ValueError):
         CommonName.from_dict_(d)
Example #22
0
 def test_clean_positions_removes_self(self, m_pi):
     """Remove self from positioning if specified."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 5
     p3.position = 9
     m_pi.return_value = [p1, p2, p3]
     p1.clean_positions(remove_self=True)
     assert p2.position == 1
     assert p3.position == 2
Example #23
0
 def test_clean_positions_removes_gaps(self, m_pi):
     """Remove gaps in position when cleaning."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 5
     p3.position = 9
     m_pi.return_value = [p1, p2, p3]
     p1.clean_positions()
     assert p1.position == 1
     assert p2.position == 2
     assert p3.position == 3
Example #24
0
    def test_dict__to_from_dict_(self, m_iq, m_cq):
        """Create new CommonName equal to CN.dict_

        Note:

        grows_with is excluded because that must be handled by a different
        function.
        """
        m_cq.get.return_value = None
        cn = CommonName()
        idx = Index()
        m_iq.get.return_value = idx
        idx.id = 1
        cn.id = 42
        cn.index = idx
        cn.name = 'Annual'
        cn.slug = 'annual'
        cn.description = 'Not built to last.'
        cn.instructions = 'Plant them.'
        cn.visible = True
        d = cn.dict_
        assert CommonName.from_dict_(d)
 def test_cv_slugs_not_in_cultivar(self, app, db):
     """Return 404 if slugs return db entries, but entry not in cultivar."""
     app.config["SHOW_CULTIVAR_PAGES"] = True
     idx1 = Index()
     idx2 = Index()
     cn1 = CommonName()
     cn2 = CommonName()
     cultivar = Cultivar()
     db.session.add_all([idx1, idx2, cn1, cn2, cultivar])
     idx1.name = "Perennial Flower"
     idx2.name = "Long Hair"
     cn1.name = "Foxglove"
     cn2.name = "Persian"
     cultivar.name = "Foxy"
     cultivar.common_name = cn1
     db.session.commit()
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug=idx1.slug, cn_slug=cn2.slug, cv_slug=cultivar.slug))
     assert rv.status_code == 404
     with app.test_client() as tc:
         rv = tc.get(url_for("seeds.cultivar", idx_slug=idx2.slug, cn_slug=cn1.slug, cv_slug=cultivar.slug))
     assert rv.status_code == 404
Example #26
0
 def test_dict__to_from_dict__(self, m_q):
     """An Index.dict_ fed to Index.from_dict_ creates identical Index."""
     m_q.get.return_value = None
     idx1 = Index()
     idx1.id = 42
     idx1.position = 3
     idx1.name = 'Annual'
     idx1.slug = 'annual'
     idx1.description = 'Not built to last.'
     d = idx1.dict_
     assert Index.from_dict_(d) == idx1
Example #27
0
 def test_last(self, m_pi):
     """Return the highest positioned instance."""
     p1 = Index()
     p2 = Index()
     p3 = Index()
     p1.position = 1
     p2.position = 2
     p3.position = 3
     m_pi.return_value = [p1, p2, p3]
     p = Index()
     assert p.last is p3
 def test_select_field_choices_with_model_by_name(self, db):
     """Generate tuple list from queried items ordered by name."""
     idx1 = Index(name='Perennial')
     idx2 = Index(name='Annual')
     idx3 = Index(name='Rock')
     idx1.id = 1
     idx2.id = 2
     idx3.id = 3
     db.session.add_all([idx1, idx2, idx3])
     db.session.flush()
     stls = select_field_choices(model=Index,
                                 title_attribute='name',
                                 order_by='name')
     assert stls == [(2, 'Annual'), (1, 'Perennial'), (3, 'Rock')]
Example #29
0
    def save_row_to_db(self, row, stream=sys.stdout):
        """Save a row representing in Index to the database.

        Args:
            row: The number of the row to save.
            stream: Optional IO stream to print messages to.

        Returns:
            bool: `True` if changes have been made, `False` if not.
        """
        name = dbify(self.cell(row, self.cols['Index']).value)
        description = self.cell(row, self.cols['Description']).value

        print('-- BEGIN editing/creating Index \'{0}\' from row #{1}. --'
              .format(name, row), file=stream)
        edited = False
        idx = Index.get_or_create(name=name, stream=stream)
        if idx.created:
            edited = True
            db.session.add(idx)
        if description != idx.description:
            edited = True
            if description:
                idx.description = description
                print('Description for the Index \'{0}\' set to: {1}'
                      .format(idx.name, idx.description), file=stream)
            elif idx.description:
                idx.description = None
                print('Description for the Index \'{0}\' has been cleared.'
                      .format(idx.name), file=stream)
        if edited:
            db.session.commit()
            print('Changes to Index \'{0}\' have been flushed to the database.'
                  .format(idx.name), file=stream)
        else:
            print('No changes were made to the Index \'{0}\'.'
                  .format(idx.name), file=stream)
        print('-- END editing/creating Index \'{0}\' from row #{1}. --'
              .format(idx.name, row), file=stream)
        return edited
Example #30
0
def add_index_to_database(d):
    print('Adding index {} to the database...'.format(d['name']))
    idx = Index.get_or_create(d['name'])
    db.session.add(idx)
    db.session.flush()
    idx.slug = d['slug']
    idx.description = d['description']
    if 'annual' in idx.slug:
        idx.thumbnail = download_image(
            'https://www.swallowtailgardenseeds.com/images/index-image-links'
            '/annual-flower-seeds4.jpg'
        )
    elif 'perennial' in idx.slug:
        idx.thumbnail = download_image(
            'https://www.swallowtailgardenseeds.com/images/index-image-links'
            '/perennial-flower-seeds.jpg'
        )
    elif 'vine' in idx.slug:
        idx.thumbnail = download_image(
            'https://www.swallowtailgardenseeds.com/images/index-image-links'
            '/flowering-vine-seeds2.jpg'
        )
    elif 'vegetable' in idx.slug:
        idx.thumbnail = download_image(
            'https://www.swallowtailgardenseeds.com/images/index-image-links'
            '/vegetable-seeds2.jpg'
        )
    elif 'herb' in idx.slug:
        idx.thumbnail = download_image(
            'https://www.swallowtailgardenseeds.com/images/index-image-links'
            '/herb-seeds2.jpg'
        )
    idx.common_names = list(generate_common_names(idx, d['common_names']))
    db.session.flush()
    idx.common_names = sorted(idx.common_names, key=lambda x: x.list_as)
    idx.common_names.reorder()
    db.session.commit()
    print('Finished adding {} to the database.'.format(d['name']))