Example #1
0
class Computer(Device):
    __doc__ = m.Computer.__doc__
    components = NestedOn(
        'Component',
        many=True,
        dump_only=True,
        collection_class=OrderedSet,
        description='The components that are inside this computer.')
    chassis = EnumField(enums.ComputerChassis,
                        required=True,
                        description=m.Computer.chassis.comment)
    ram_size = Integer(dump_only=True,
                       data_key='ramSize',
                       description=m.Computer.ram_size.__doc__)
    data_storage_size = Integer(
        dump_only=True,
        data_key='dataStorageSize',
        description=m.Computer.data_storage_size.__doc__)
    processor_model = Str(dump_only=True,
                          data_key='processorModel',
                          description=m.Computer.processor_model.__doc__)
    graphic_card_model = Str(dump_only=True,
                             data_key='graphicCardModel',
                             description=m.Computer.graphic_card_model.__doc__)
    network_speeds = List(Integer(dump_only=True),
                          dump_only=True,
                          data_key='networkSpeeds',
                          description=m.Computer.network_speeds.__doc__)
    privacy = NestedOn('Event',
                       many=True,
                       dump_only=True,
                       collection_class=set,
                       description=m.Computer.privacy.__doc__)
Example #2
0
class DataStorage(Component):
    size = Integer(validate=Range(0, 10**8),
                   unit=UnitCodes.mbyte,
                   description='The size of the hard-drive in MB.')
    erasure = NestedOn('EraseBasic', load_only=True)
    tests = NestedOn('TestHardDrive', many=True, load_only=True)
    benchmarks = NestedOn('BenchmarkHardDrive', load_only=True, many=True)
Example #3
0
class Lot(Thing):
    id = f.UUID(dump_only=True)
    name = SanitizedStr(validate=f.validate.Length(max=STR_SIZE),
                        required=True)
    description = SanitizedStr(description=m.Lot.description.comment)
    closed = f.Boolean(missing=False, description=m.Lot.closed.comment)
    devices = NestedOn(s_device.Device, many=True, dump_only=True)
    children = NestedOn('Lot', many=True, dump_only=True)
    parents = NestedOn('Lot', many=True, dump_only=True)
    url = URL(dump_only=True, description=m.Lot.url.__doc__)
Example #4
0
class Tag(Thing):
    id = SanitizedStr(lower=True,
                      description=m.Tag.id.comment,
                      validator=without_slash,
                      required=True)
    provider = URL(description=m.Tag.provider.comment, validator=without_slash)
    device = NestedOn(Device, dump_only=True)
    org = NestedOn(Organization, collection_class=OrderedSet, only_query='id')
    secondary = SanitizedStr(lower=True, description=m.Tag.secondary.comment)
    printable = Boolean(dump_only=True, decsription=m.Tag.printable.__doc__)
    url = URL(dump_only=True, description=m.Tag.url.__doc__)
Example #5
0
class Trade(EventWithMultipleDevices):
    __doc__ = m.Trade.__doc__
    shipping_date = DateTime(data_key='shippingDate')
    invoice_number = SanitizedStr(validate=Length(max=STR_SIZE),
                                  data_key='invoiceNumber')
    price = NestedOn(Price)
    to = NestedOn(s_agent.Agent,
                  only_query='id',
                  required=True,
                  comment=m.Trade.to_comment)
    confirms = NestedOn(Organize)
Example #6
0
class Device(Thing):
    # todo id is dump_only except when in Snapshot
    id = Integer(description='The identifier of the device for this database.')
    hid = Str(
        dump_only=True,
        description='The Hardware ID is the unique ID traceability systems '
        'use to ID a device globally.')
    tags = NestedOn('Tag', many=True, collection_class=OrderedSet)
    model = Str(validate=Length(max=STR_BIG_SIZE))
    manufacturer = Str(validate=Length(max=STR_SIZE))
    serial_number = Str(data_key='serialNumber')
    product_id = Str(data_key='productId')
    weight = Float(validate=Range(0.1, 3),
                   unit=UnitCodes.kgm,
                   description='The weight of the device in Kgm.')
    width = Float(validate=Range(0.1, 3),
                  unit=UnitCodes.m,
                  description='The width of the device in meters.')
    height = Float(validate=Range(0.1, 3),
                   unit=UnitCodes.m,
                   description='The height of the device in meters.')
    events = NestedOn('Event', many=True, dump_only=True)
    events_one = NestedOn('Event',
                          many=True,
                          load_only=True,
                          collection_class=OrderedSet)

    @pre_load
    def from_events_to_events_one(self, data: dict):
        """
        Not an elegant way of allowing submitting events to a device
        (in the context of Snapshots) without creating an ``events``
        field at the model (which is not possible).
        :param data:
        :return:
        """
        # Note that it is secure to allow uploading events_one
        # as the only time an user can send a device object is
        # in snapshots.
        data['events_one'] = data.pop('events', [])
        return data

    @post_load
    def validate_snapshot_events(self, data):
        """Validates that only snapshot-related events can be uploaded."""
        from ereuse_devicehub.resources.event.models import EraseBasic, Test, Rate, Install, \
            Benchmark
        for event in data['events_one']:
            if not isinstance(event,
                              (Install, EraseBasic, Rate, Test, Benchmark)):
                raise ValidationError('You cannot upload {}'.format(event),
                                      field_names=['events'])
Example #7
0
class Event(Thing):
    id = UUID(dump_only=True)
    name = String(default='',
                  validate=Length(STR_BIG_SIZE),
                  description=m.Event.name.comment)
    date = DateTime('iso', description=m.Event.date.comment)
    error = Boolean(default=False, description=m.Event.error.comment)
    incidence = Boolean(default=False, description=m.Event.incidence.comment)
    snapshot = NestedOn('Snapshot', dump_only=True)
    components = NestedOn(Component, dump_only=True, many=True)
    description = String(default='', description=m.Event.description.comment)
    author = NestedOn(User, dump_only=True, exclude=('token', ))
    closed = Boolean(missing=True, description=m.Event.closed.comment)
Example #8
0
class Allocate(EventWithMultipleDevices):
    __doc__ = m.Allocate.__doc__
    to = NestedOn(s_user.User,
                  description='The user the devices are allocated to.')
    organization = SanitizedStr(validate=Length(max=STR_SIZE),
                                description='The organization where the '
                                'user was when this happened.')
Example #9
0
class TradeDocument(Thing):
    __doc__ = m.TradeDocument.__doc__
    id = Integer(description=m.TradeDocument.id.comment, dump_only=True)
    date = DateTime(required=False, description=m.TradeDocument.date.comment)
    id_document = SanitizedStr(data_key='documentId',
                               default='',
                               description=m.TradeDocument.id_document.comment)
    description = SanitizedStr(default='',
                               description=m.TradeDocument.description.comment,
                               validate=validate.Length(max=500))
    file_name = SanitizedStr(data_key='filename',
                             default='',
                             description=m.TradeDocument.file_name.comment,
                             validate=validate.Length(max=100))
    file_hash = SanitizedStr(data_key='hash',
                             default='',
                             description=m.TradeDocument.file_hash.comment,
                             validate=validate.Length(max=64))
    url = URL(description=m.TradeDocument.url.comment)
    lot = NestedOn('Lot',
                   only_query='id',
                   description=m.TradeDocument.lot.__doc__)
    trading = SanitizedStr(dump_only=True, description='')
    weight = Float(required=False, description=m.TradeDocument.weight.comment)
    total_weight = Float(required=False,
                         description=m.TradeDocument.weight.comment)
Example #10
0
class Tag(Thing):
    id = String(description='The ID of the tag.',
                validator=lambda x: '/' not in x,
                required=True)
    provider = URL(description='The provider URL.')
    device = NestedOn(Device, description='The device linked to this tag.')
    org = String(description='The organization that issued the tag.')
Example #11
0
class Snapshot(EventWithOneDevice):
    """
    The Snapshot updates the state of the device with information about
    its components and events performed at them.

    See docs for more info.
    """
    uuid = UUID(required=True)
    software = EnumField(
        SnapshotSoftware,
        required=True,
        description='The software that generated this Snapshot.')
    version = Version(required=True,
                      description='The version of the software.')
    events = NestedOn(Event, many=True, dump_only=True)
    expected_events = List(
        EnumField(SnapshotExpectedEvents),
        data_key='expectedEvents',
        description='Keep open this Snapshot until the following events'
        'are performed. Setting this value will activate'
        'the async Snapshot.')

    device = NestedOn(Device)
    elapsed = TimeDelta(precision=TimeDelta.SECONDS, required=True)
    components = NestedOn(
        Component,
        many=True,
        description='A list of components that are inside of the device'
        'at the moment of this Snapshot.'
        'Order is preserved, so the component num 0 when'
        'submitting is the component num 0 when returning it back.')

    @validates_schema
    def validate_workbench_version(self, data: dict):
        if data['software'] == SnapshotSoftware.Workbench:
            if data['version'] < app.config['MIN_WORKBENCH']:
                raise ValidationError(
                    'Min. supported Workbench algorithm_version is '
                    '{}'.format(app.config['MIN_WORKBENCH']),
                    field_names=['version'])

    @validates_schema
    def validate_components_only_workbench(self, data: dict):
        if data['software'] != SnapshotSoftware.Workbench:
            if data['components'] is not None:
                raise ValidationError('Only Workbench can add component info',
                                      field_names=['components'])
Example #12
0
class EraseBasic(EventWithOneDevice):
    start_time = DateTime(required=True, data_key='startTime')
    end_time = DateTime(required=True, data_key='endTime')
    secure_random_steps = Integer(validate=Range(min=0),
                                  required=True,
                                  data_key='secureRandomSteps')
    clean_with_zeros = Boolean(required=True, data_key='cleanWithZeros')
    steps = NestedOn('Step', many=True, required=True)
Example #13
0
class DataStorage(Component):
    __doc__ = m.DataStorage.__doc__

    size = Integer(validate=Range(0, 10**8),
                   unit=UnitCodes.mbyte,
                   description=m.DataStorage.size.comment)
    interface = EnumField(enums.DataStorageInterface)
    privacy = NestedOn('Event', dump_only=True)
Example #14
0
class Computer(Device):
    __doc__ = m.Computer.__doc__
    # TODO TimeOut 1. Comment components if there are time out.
    components = NestedOn(
        'Component',
        many=True,
        dump_only=True,
        collection_class=OrderedSet,
        description='The components that are inside this computer.')
    chassis = EnumField(enums.ComputerChassis,
                        description=m.Computer.chassis.comment)
    ram_size = Integer(dump_only=True,
                       data_key='ramSize',
                       description=m.Computer.ram_size.__doc__)
    data_storage_size = Integer(
        dump_only=True,
        data_key='dataStorageSize',
        description=m.Computer.data_storage_size.__doc__)
    processor_model = Str(dump_only=True,
                          data_key='processorModel',
                          description=m.Computer.processor_model.__doc__)
    graphic_card_model = Str(dump_only=True,
                             data_key='graphicCardModel',
                             description=m.Computer.graphic_card_model.__doc__)
    network_speeds = List(Integer(dump_only=True),
                          dump_only=True,
                          data_key='networkSpeeds',
                          description=m.Computer.network_speeds.__doc__)
    privacy = NestedOn('Action',
                       many=True,
                       dump_only=True,
                       collection_class=set,
                       description=m.Computer.privacy.__doc__)
    amount = Integer(validate=f.validate.Range(min=0, max=100),
                     description=m.Computer.amount.__doc__)
    # author_id = NestedOn(s_user.User, only_query='author_id')
    owner_id = UUID(data_key='ownerID')
    transfer_state = EnumField(enums.TransferState,
                               description=m.Computer.transfer_state.comment)
    receiver_id = UUID(data_key='receiverID')
Example #15
0
class Event(Thing):
    __doc__ = m.Event.__doc__
    id = UUID(dump_only=True)
    name = SanitizedStr(default='',
                        validate=Length(max=STR_BIG_SIZE),
                        description=m.Event.name.comment)
    closed = Boolean(missing=True, description=m.Event.closed.comment)
    severity = EnumField(Severity, description=m.Event.severity.comment)
    description = SanitizedStr(default='',
                               description=m.Event.description.comment)
    start_time = DateTime(data_key='startTime',
                          description=m.Event.start_time.comment)
    end_time = DateTime(data_key='endTime',
                        description=m.Event.end_time.comment)
    snapshot = NestedOn('Snapshot', dump_only=True)
    agent = NestedOn(s_agent.Agent, description=m.Event.agent_id.comment)
    author = NestedOn(s_user.User, dump_only=True, exclude=('token', ))
    components = NestedOn(s_device.Component, dump_only=True, many=True)
    parent = NestedOn(s_device.Computer,
                      dump_only=True,
                      description=m.Event.parent_id.comment)
    url = URL(dump_only=True, description=m.Event.url.__doc__)
Example #16
0
class User(Thing):
    id = UUID(dump_only=True)
    email = Email(required=True)
    password = SanitizedStr(load_only=True, required=True)
    individuals = NestedOn(Individual, many=True, dump_only=True)
    name = SanitizedStr()
    token = String(
        dump_only=True,
        description=
        'Use this token in an Authorization header to access the app.'
        'The token can change overtime.')
    inventories = NestedOn(Inventory, many=True, dump_only=True)
    code = String(dump_only=True, description='Code of inactive accounts')

    def __init__(self,
                 only=None,
                 exclude=('token', ),
                 prefix='',
                 many=False,
                 context=None,
                 load_only=(),
                 dump_only=(),
                 partial=False):
        """Instantiates the User.

        By default we exclude token from both load/dump
        so they are not taken / set in normal usage by mistake.
        """
        super().__init__(only, exclude, prefix, many, context, load_only,
                         dump_only, partial)

    @post_dump
    def base64encode_token(self, data: dict):
        """Encodes the token to base64 so clients don't have to."""
        if 'token' in data:
            # In many cases we don't dump the token (ex. relationships)
            # Framework needs ':' at the end
            data['token'] = auth.Auth.encode(data['token'])
        return data
Example #17
0
class Deliverynote(Thing):
    id = f.UUID(dump_only=True)
    document_id = SanitizedStr(validate=f.validate.Length(max=STR_SIZE),
                               required=True,
                               data_key='documentID')
    creator = NestedOn(s_user.User, dump_only=True)
    supplier_email = SanitizedStr(validate=f.validate.Length(max=STR_SIZE),
                                  load_only=True,
                                  required=True,
                                  data_key='supplierEmail')
    supplier = NestedOn(s_user.User, dump_only=True)
    receiver = NestedOn(s_user.User, dump_only=True)
    date = f.DateTime('iso', required=True)
    amount = f.Integer(validate=f.validate.Range(min=0, max=100),
                       description=m.Deliverynote.amount.__doc__)
    expected_devices = f.List(f.Dict,
                              required=True,
                              data_key='expectedDevices')
    transferred_devices = f.List(f.Integer(),
                                 required=False,
                                 data_key='transferredDevices')
    transfer_state = EnumField(TransferState,
                               description=m.Lot.transfer_state.comment)
Example #18
0
class AggregateRate(Rate):
    __doc__ = m.AggregateRate.__doc__
    workbench = NestedOn(WorkbenchRate,
                         dump_only=True,
                         description=m.AggregateRate.workbench_id.comment)
    manual = NestedOn(ManualRate,
                      dump_only=True,
                      description=m.AggregateRate.manual_id.comment)
    processor = Float(dump_only=True)
    ram = Float(dump_only=True)
    data_storage = Float(dump_only=True)
    graphic_card = Float(dump_only=True)
    bios = EnumField(Bios, dump_only=True)
    bios_range = EnumField(Bios,
                           description=m.WorkbenchRate.bios_range.comment,
                           data_key='biosRange')
    appearance_range = EnumField(
        AppearanceRange,
        required=True,
        data_key='appearanceRange',
        description=m.ManualRate.appearance_range.comment)
    functionality_range = EnumField(
        FunctionalityRange,
        required=True,
        data_key='functionalityRange',
        description=m.ManualRate.functionality_range.comment)
    labelling = Boolean(description=m.ManualRate.labelling.comment)
    data_storage_range = EnumField(RatingRange,
                                   dump_only=True,
                                   data_key='dataStorageRange')
    ram_range = EnumField(RatingRange, dump_only=True, data_key='ramRange')
    processor_range = EnumField(RatingRange,
                                dump_only=True,
                                data_key='processorRange')
    graphic_card_range = EnumField(RatingRange,
                                   dump_only=True,
                                   data_key='graphicCardRange')
Example #19
0
class Price(EventWithOneDevice):
    __doc__ = m.Price.__doc__
    currency = EnumField(Currency,
                         required=True,
                         description=m.Price.currency.comment)
    price = Decimal(places=m.Price.SCALE,
                    rounding=m.Price.ROUND,
                    required=True,
                    description=m.Price.price.comment)
    software = EnumField(PriceSoftware,
                         dump_only=True,
                         description=m.Price.software.comment)
    version = Version(dump_only=True, description=m.Price.version.comment)
    rating = NestedOn(AggregateRate,
                      dump_only=True,
                      description=m.Price.rating_id.comment)
Example #20
0
class Device(Thing):
    __doc__ = m.Device.__doc__
    id = Integer(description=m.Device.id.comment, dump_only=True)
    hid = SanitizedStr(lower=True,
                       dump_only=True,
                       description=m.Device.hid.comment)
    tags = NestedOn('Tag',
                    many=True,
                    collection_class=OrderedSet,
                    description='A set of tags that identify the device.')
    model = SanitizedStr(lower=True,
                         validate=Length(max=STR_BIG_SIZE),
                         description=m.Device.model.comment)
    manufacturer = SanitizedStr(lower=True,
                                validate=Length(max=STR_SIZE),
                                description=m.Device.manufacturer.comment)
    serial_number = SanitizedStr(lower=True,
                                 validate=Length(max=STR_BIG_SIZE),
                                 data_key='serialNumber')
    brand = SanitizedStr(validate=Length(max=STR_BIG_SIZE),
                         description=m.Device.brand.comment)
    generation = Integer(validate=Range(1, 100),
                         description=m.Device.generation.comment)
    weight = Float(validate=Range(0.1, 5),
                   unit=UnitCodes.kgm,
                   description=m.Device.weight.comment)
    width = Float(validate=Range(0.1, 5),
                  unit=UnitCodes.m,
                  description=m.Device.width.comment)
    height = Float(validate=Range(0.1, 5),
                   unit=UnitCodes.m,
                   description=m.Device.height.comment)
    depth = Float(validate=Range(0.1, 5),
                  unit=UnitCodes.m,
                  description=m.Device.depth.comment)
    events = NestedOn('Event',
                      many=True,
                      dump_only=True,
                      description=m.Device.events.__doc__)
    events_one = NestedOn('Event',
                          many=True,
                          load_only=True,
                          collection_class=OrderedSet)
    problems = NestedOn('Event',
                        many=True,
                        dump_only=True,
                        description=m.Device.problems.__doc__)
    url = URL(dump_only=True, description=m.Device.url.__doc__)
    lots = NestedOn(
        'Lot',
        many=True,
        dump_only=True,
        description='The lots where this device is directly under.')
    rate = NestedOn('AggregateRate',
                    dump_only=True,
                    description=m.Device.rate.__doc__)
    price = NestedOn('Price',
                     dump_only=True,
                     description=m.Device.price.__doc__)
    trading = EnumField(states.Trading,
                        dump_only=True,
                        description=m.Device.trading.__doc__)
    physical = EnumField(states.Physical,
                         dump_only=True,
                         description=m.Device.physical.__doc__)
    physical_possessor = NestedOn('Agent',
                                  dump_only=True,
                                  data_key='physicalPossessor')
    production_date = DateTime('iso',
                               description=m.Device.updated.comment,
                               data_key='productionDate')
    working = NestedOn('Event',
                       many=True,
                       dump_only=True,
                       description=m.Device.working.__doc__)

    @pre_load
    def from_events_to_events_one(self, data: dict):
        """
        Not an elegant way of allowing submitting events to a device
        (in the context of Snapshots) without creating an ``events``
        field at the model (which is not possible).
        :param data:
        :return:
        """
        # Note that it is secure to allow uploading events_one
        # as the only time an user can send a device object is
        # in snapshots.
        data['events_one'] = data.pop('events', [])
        return data

    @post_load
    def validate_snapshot_events(self, data):
        """Validates that only snapshot-related events can be uploaded."""
        from ereuse_devicehub.resources.event.models import EraseBasic, Test, Rate, Install, \
            Benchmark
        for event in data['events_one']:
            if not isinstance(event,
                              (Install, EraseBasic, Rate, Test, Benchmark)):
                raise ValidationError('You cannot upload {}'.format(event),
                                      field_names=['events'])
Example #21
0
class EventWithOneDevice(Event):
    device = NestedOn(Device)
Example #22
0
class Component(Device):
    parent = NestedOn(Device, dump_only=True)
Example #23
0
class EventWithMultipleDevices(Event):
    devices = NestedOn(Device, many=True)
Example #24
0
class Allocate(EventWithMultipleDevices):
    to = NestedOn(User, description='The user the devices are allocated to.')
    organization = String(
        validate=Length(STR_SIZE),
        description='The organization where the user was when this happened.')
Example #25
0
class EraseBasic(EventWithOneDevice):
    __doc__ = m.EraseBasic.__doc__
    steps = NestedOn('Step', many=True)
    standards = f.List(EnumField(enums.ErasureStandards), dump_only=True)
    certificate = URL(dump_only=True)
Example #26
0
class EventWithMultipleDevices(Event):
    __doc__ = m.EventWithMultipleDevices.__doc__
    devices = NestedOn(s_device.Device,
                       many=True,
                       only_query='id',
                       collection_class=OrderedSet)
Example #27
0
class Component(Device):
    __doc__ = m.Component.__doc__

    parent = NestedOn(Device, dump_only=True)
Example #28
0
class Computer(Device):
    components = NestedOn('Component',
                          many=True,
                          dump_only=True,
                          collection_class=OrderedSet)
    pass
Example #29
0
class EventWithOneDevice(Event):
    __doc__ = m.EventWithOneDevice.__doc__
    device = NestedOn(s_device.Device, only_query='id')
Example #30
0
class Snapshot(EventWithOneDevice):
    __doc__ = m.Snapshot.__doc__
    """
    The Snapshot updates the state of the device with information about
    its components and events performed at them.

    See docs for more info.
    """
    uuid = UUID()
    software = EnumField(
        SnapshotSoftware,
        required=True,
        description='The software that generated this Snapshot.')
    version = Version(required=True,
                      description='The version of the software.')
    events = NestedOn(Event, many=True, dump_only=True)
    expected_events = List(
        EnumField(SnapshotExpectedEvents),
        data_key='expectedEvents',
        description='Keep open this Snapshot until the following events'
        'are performed. Setting this value will activate'
        'the async Snapshot.')

    elapsed = TimeDelta(precision=TimeDelta.SECONDS)
    components = NestedOn(
        s_device.Component,
        many=True,
        description='A list of components that are inside of the device'
        'at the moment of this Snapshot.'
        'Order is preserved, so the component num 0 when'
        'submitting is the component num 0 when returning it back.')

    @validates_schema
    def validate_workbench_version(self, data: dict):
        if data['software'] == SnapshotSoftware.Workbench:
            if data['version'] < app.config['MIN_WORKBENCH']:
                raise ValidationError('Min. supported Workbench version is '
                                      '{} but yours is {}.'.format(
                                          app.config['MIN_WORKBENCH'],
                                          data['version']),
                                      field_names=['version'])

    @validates_schema
    def validate_components_only_workbench(self, data: dict):
        if data['software'] != SnapshotSoftware.Workbench:
            if data.get('components', None) is not None:
                raise ValidationError('Only Workbench can add component info',
                                      field_names=['components'])

    @validates_schema
    def validate_only_workbench_fields(self, data: dict):
        """Ensures workbench has ``elapsed`` and ``uuid`` and no others."""
        # todo test
        if data['software'] == SnapshotSoftware.Workbench:
            if not data.get('uuid', None):
                raise ValidationError(
                    'Snapshots from Workbench must have uuid',
                    field_names=['uuid'])
            if data.get('elapsed', None) is None:
                raise ValidationError(
                    'Snapshots from Workbench must have elapsed',
                    field_names=['elapsed'])
        else:
            if data.get('uuid', None):
                raise ValidationError(
                    'Only Snapshots from Workbench can have uuid',
                    field_names=['uuid'])
            if data.get('elapsed', None):
                raise ValidationError(
                    'Only Snapshots from Workbench can have elapsed',
                    field_names=['elapsed'])