Bläddra i källkod

Add 'unplanned items' model

theenglishway (time) 6 år sedan
förälder
incheckning
30c48d8689

+ 29 - 7
pyplanner/cli.py

@@ -95,9 +95,16 @@ def sprint(ctx):
 
 @main.group()
 @click.pass_context
-def item(ctx):
-    """Handle items"""
-    ctx.obj['model'] = Item
+def planned(ctx):
+    """Handle planned items"""
+    ctx.obj['model'] = PlannedItem
+
+
+@main.group()
+@click.pass_context
+def unplanned(ctx):
+    """Handle unplanned items"""
+    ctx.obj['model'] = UnplannedItem
 
 
 @main.group()
@@ -122,14 +129,29 @@ def new(ctx, **data):
         click.echo(Term.failure(e.args[0]))
 
 
-@item.command('new')
+@planned.command('new')
 @click.option('--name', prompt='Name')
 @click.option('--description', prompt='Description')
 @click.option('--collection_id', type=int, prompt='Collection ID')
-@click.option('--type', prompt='Type', type=click.Choice([v.value for v in ItemType]))
+@click.option('--type', prompt='Type', type=click.Choice([v.value for v in PlannedItemType]))
 @click.pass_context
-def new_item(ctx, **data):
-    model = Item
+def new_planned(ctx, **data):
+    model = ctx.obj['model']
+    db = ctx.obj['db']
+    try:
+        instance = db.create(model, data)
+        click.echo(Term.success(instance))
+    except ValueError as e:
+        click.echo(Term.failure(e.args[0]))
+
+
+@unplanned.command('new')
+@click.option('--name', prompt='Name')
+@click.option('--description', prompt='Description')
+@click.option('--type', prompt='Type', type=click.Choice([v.value for v in UnplannedItemType]))
+@click.pass_context
+def new_unplanned(ctx, **data):
+    model = ctx.obj['model']
     db = ctx.obj['db']
     try:
         instance = db.create(model, data)

+ 9 - 3
pyplanner/models/__init__.py

@@ -47,9 +47,12 @@ class BaseEnum:
 from .collections import Collection
 from .milestones import Milestone
 from .sprints import Sprint
-from .items import Item, ItemType
-from .planned import (Limitation, Constraint, Feature, Unknown,
+from .items import Item
+from .planned import (PlannedItem, PlannedItemType,
+                      Limitation, Constraint, Feature, Unknown,
                       ItemPriority, Length)
+from .unplanned import (UnplannedItem, UnplannedItemType,
+                        Idea, Experimentation)
 from .comments import Comment
 
 
@@ -58,7 +61,10 @@ __all__ = [
     'Milestone',
     'Sprint',
     'Item',
+    'PlannedItem', 'PlannedItemType',
     'Limitation', 'Constraint', 'Feature', 'Unknown',
-    'ItemType', 'ItemPriority', 'Length',
+    'ItemPriority', 'Length',
+    'UnplannedItem', 'UnplannedItemType',
+    'Experimentation', 'Idea',
     'Comment'
 ]

+ 2 - 31
pyplanner/models/items.py

@@ -1,26 +1,12 @@
 from pyplanner.database import SQLABase
-from pyplanner.models import Base, BaseEnum
+from pyplanner.models import Base
 from sqlalchemy import Column, Integer, String, Text
-from sqlalchemy.ext.hybrid import hybrid_property
 from pydantic import BaseModel
-from enum import Enum
-
-
-
-class ItemType(BaseEnum, Enum):
-    ITEM = 'none'
-
-    PLANNED = 'planned'
-    LIMITATION = 'lim'
-    FEATURE = 'feat'
-    CONSTRAINT = 'cons'
-    UNKNOWN = 'unk'
 
 
 class SchemaItem(BaseModel):
     name: str
     description: str
-    type: ItemType
     uuid: str
 
 
@@ -33,22 +19,7 @@ class Item(SQLABase, Base):
     name = Column(String)
     description = Column(Text)
     uuid = Column(String)
-    _type = Column(String)
-
-    @hybrid_property
-    def type(self):
-        return ItemType(self._type)
-
-    @type.setter
-    def type(self, value):
-        self._type = value.value
-
-    @type.expression
-    def type(cls):
-        return cls._type
 
     __mapper_args__ = {
-        'polymorphic_on': _type,
-        'polymorphic_identity': ItemType.ITEM.value,
         'with_polymorphic': '*'
-    }
+    }

+ 33 - 6
pyplanner/models/planned.py

@@ -5,10 +5,18 @@ from sqlalchemy import Column, Integer, String, ForeignKey
 from sqlalchemy.orm import relationship, backref
 from sqlalchemy.ext.hybrid import hybrid_property
 
-from .items import Item, SchemaItem, ItemType
+from .items import Item, SchemaItem
 from . import BaseEnum
 
 
+class PlannedItemType(BaseEnum, Enum):
+    PLANNED = 'planned'
+    LIMITATION = 'lim'
+    FEATURE = 'feat'
+    CONSTRAINT = 'cons'
+    UNKNOWN = 'unk'
+
+
 @total_ordering
 class Length(BaseEnum, Enum):
     MINUTES = 'mi'
@@ -52,6 +60,8 @@ class ItemPriority(BaseEnum, Enum):
 
 
 class SchemaPlannedItem(SchemaItem):
+    type: PlannedItemType
+
     collection_id: int
 
     priority: ItemPriority = ItemPriority.SO_SO
@@ -59,8 +69,11 @@ class SchemaPlannedItem(SchemaItem):
 
 
 class PlannedItem(Item):
+    _schema = SchemaPlannedItem
+
     __tablename__ = 'planned_items'
     id = Column(Integer, ForeignKey('items.id'), primary_key=True)
+    _type = Column(String)
 
     collection_id = Column(Integer, ForeignKey('collections.id'))
     collection = relationship('Collection', backref=backref('planned_items'))
@@ -69,9 +82,23 @@ class PlannedItem(Item):
     _length = Column(String)
 
     __mapper_args__ = {
-        'polymorphic_identity': ItemType.PLANNED.value
+        'polymorphic_on': _type,
+        'polymorphic_identity': PlannedItemType.PLANNED.value,
+        'with_polymorphic': '*'
     }
 
+    @hybrid_property
+    def type(self):
+        return PlannedItemType(self._type)
+
+    @type.setter
+    def type(self, value):
+        self._type = value.value
+
+    @type.expression
+    def type(cls):
+        return cls._type
+
     @hybrid_property
     def length(self):
         return Length(self._length)
@@ -99,23 +126,23 @@ class PlannedItem(Item):
 
 class Limitation(PlannedItem):
     __mapper_args__ = {
-        'polymorphic_identity': ItemType.LIMITATION.value
+        'polymorphic_identity': PlannedItemType.LIMITATION.value
     }
 
 
 class Feature(PlannedItem):
     __mapper_args__ = {
-        'polymorphic_identity': ItemType.FEATURE.value
+        'polymorphic_identity': PlannedItemType.FEATURE.value
     }
 
 
 class Constraint(PlannedItem):
     __mapper_args__ = {
-        'polymorphic_identity': ItemType.CONSTRAINT.value
+        'polymorphic_identity': PlannedItemType.CONSTRAINT.value
     }
 
 
 class Unknown(PlannedItem):
     __mapper_args__ = {
-        'polymorphic_identity': ItemType.UNKNOWN.value
+        'polymorphic_identity': PlannedItemType.UNKNOWN.value
     }

+ 55 - 0
pyplanner/models/unplanned.py

@@ -0,0 +1,55 @@
+from enum import Enum
+
+from sqlalchemy import Column, Integer, String, ForeignKey
+from sqlalchemy.ext.hybrid import hybrid_property
+
+from .items import Item, SchemaItem
+from . import BaseEnum
+
+
+class UnplannedItemType(BaseEnum, Enum):
+    UNPLANNED = 'unplanned'
+    IDEA = 'idea'
+    EXPERIMENTATION = 'xp'
+
+
+class SchemaUnplannedItem(SchemaItem):
+    type: UnplannedItemType
+
+
+class UnplannedItem(Item):
+    _schema = SchemaUnplannedItem
+
+    __tablename__ = 'unplanned_items'
+    id = Column(Integer, ForeignKey('items.id'), primary_key=True)
+    _type = Column(String)
+
+    __mapper_args__ = {
+        'polymorphic_on': _type,
+        'polymorphic_identity': UnplannedItemType.UNPLANNED.value,
+        'with_polymorphic': '*'
+    }
+
+    @hybrid_property
+    def type(self):
+        return UnplannedItemType(self._type)
+
+    @type.setter
+    def type(self, value):
+        self._type = value.value
+
+    @type.expression
+    def type(cls):
+        return cls._type
+
+
+class Idea(UnplannedItem):
+    __mapper_args__ = {
+        'polymorphic_identity': UnplannedItemType.IDEA.value
+    }
+
+
+class Experimentation(UnplannedItem):
+    __mapper_args__ = {
+        'polymorphic_identity': UnplannedItemType.EXPERIMENTATION.value
+    }

+ 5 - 2
pyplanner/output.py

@@ -10,9 +10,12 @@ class TerminalOutput:
             Milestone: """{{ Term.bold('Milestone') }} {{ Term.uuid(obj.short_uuid) }} # {{ obj.name }} 
     {% for item in obj.sprints %}
       {{- output(item) }}
-    {% endfor %}""",
+    {% endfor %}
+    {%- for item in obj.planned_items %}
+      {{ output(item) }}
+    {%- endfor %}""",
             Sprint: """{{ Term.bold('Sprint') }} {{ Term.uuid(obj.short_uuid) }} # {{ obj.name }} 
-    {%- for item in obj.items %}
+    {%- for item in obj.planned_items %}
       {{ output(item) }}
     {%- endfor %}""",
             Item: """{{ Term.bold(obj.type) }} {{ Term.uuid(obj.short_uuid) }} # {{ obj.name }} ({{ obj.priority }}, {{ obj.length }})