Пример #1
0
    def __init__(self, options, **kw):
        # options must be a regular list of strings, iterable is ok
        assert hasattr(options, "__iter__") and len(options) > 1
        self.options = options

        # keep provided options
        kw.update({"options": options})
    
        # set size, if not manually done...
        self.size = max(map(len, options))

        # cross-check own size with provided and so on
        if kw.get("size") is not None and self.size <= kw.get("size"):
            raise DatabaseError(
                    "provided size ({}<{}) is less than biggest " + 
                    "provided option: {}". \
                        format(kw.get("size"), self.size, ", ".join(options)))
    
        # default value -> first item of options, if no 'default' is set
        if "default" in kw:
            assert kw["default"] in options
            self.default = kw["default"]
        else:
            self.default = options[0]
        kw["default"] = self.default
        
        # call parent's ctor
        super(OptionField, self).__init__(**kw)
Пример #2
0
    def __init__(self, **kw):
        # check, if kw contains solely legal keywords
        wrong = [
            k for k in kw
            if not k in (self.accepted_keywords + self.general_keywords)
        ]
        if len(wrong) > 0:
            raise DatabaseError("Keyword(s): {} not supported by this Field: {}". \
                    format(", ".join(wrong), self.__class__.__name__))

        # setting FieldObjects as member names
        for k, v in kw.items():
            setattr(self, k, v)

        # apply the various general flags/values
        for k in self.general_keywords:
            val = kw.get(k) if k in kw else getattr(self.__class__, k)
            setattr(self, k, val)

        # keeps the explicit value of this field (and it's object, if applicable)
        self._value = self.default if not "default" in kw else kw["default"]
        self._value_obj = None

        # parent record class
        self.parent = None
        # keep the passed keyword-dict from instanciation
        self.passed_kw = kw
Пример #3
0
    def __init__(cls, name, bases, dct):

        # exclude the base class from this behaviour
        if object in bases:
            return

        cls.table = name.lower()

        # move all "*Fields" to self.fields
        cls.base_fields = {}

        # queue based descent in hierachy to find all necassary fields of
        # arbitrary depth
        workqueue = [(cls, "", att) for att in cls.__dict__.keys()]
        from fields import AbstractField, BaseFieldGroup
        while len(workqueue) > 0:
            curcls, prefix, att = workqueue.pop(0)

            # check for minimal field name length (> 2)
            if len(att) < 2:
                raise DatabaseError("For __reasons unknown__ field " + \
                                    "names must have at least 2 chars")

            # identify and setup fields inside this cls
            if not issubclass(curcls.__class__,
                              (AbstractField, BaseFieldGroup)):
                field = getattr(curcls, att)
            else:
                field = curcls

            # description TODO ;D
            if issubclass(field.__class__, AbstractField):
                cls.setup_field(prefix + att, field)

            elif issubclass(field.__class__, BaseFieldGroup):
                cls.setup_field(prefix + att, field)

                for sub_field_key, sub_field in field.grp_fields.items():
                    if issubclass(sub_field.__class__, BaseFieldGroup):
                        workqueue.append(
                            (sub_field, prefix + att + "__", sub_field_key))

                    elif issubclass(sub_field.__class__, AbstractField):
                        cls.setup_field(prefix + att + "__" + sub_field_key,
                                        sub_field)

        # init database instance for this class
        cls.database = SQLiteDatabase()
        cls.database.contribute(cls)

        # populate cls.objects
        cls.objects = DataManager(cls)
Пример #4
0
    def __call__(cls, *vargs, **kw):

        # check, if kw contains solely legal keywords
        wrong = [k for k in kw if not k in cls.keywords]
        if len(wrong) > 0:
            raise DatabaseError("Keyword(s): {} unsupported by this Field: {}".\
                    format(", ".join(wrong), cls.__class__.__name__))

        # create object instance
        out_inst = type.__call__(cls, *vargs, **kw)

        # fill in key->val from 'kw' into 'out_inst', as attributes
        for key, val in cls.keywords.items():
            if key in kw:
                setattr(out_inst, key, kw[key])
            
        return out_inst
Пример #5
0
    def __init__(cls, name, bases, dct):

        # exclude the base class from this behaviour
        if not name == "BaseRecord":
            cls.table = name.lower()

            # move all "*Fields" to self.fields and init atts to None
            cls.base_fields = {}
            for att in cls.__dict__.keys()[:]:

                # check for minimal field name length (> 2)
                if len(att) < 2:
                    raise DatabaseError(
                        "For __reasons unknown__ field names must have at least 2 chars"
                    )

                # identify and setup fields inside this record
                field = getattr(cls, att)
                from fields import AbstractField
                if issubclass(field.__class__, AbstractField):
                    cls.setup_field(att, field)

            # this does not behave as expected inside sqlite3
            # - rowid named col needs AUTOINC, which sux (performance)
            # - so omit this and use built-in rowid,
            #   which works nicely except for the unintuitive interface (select rowid, * ...)
            #
            # if there is no explicit column named: 'rowid', create one as primary_key!!!
            #if "rowid" not in cls.base_fields:
            #    from fields import IDField
            #    cls.setup_field("rowid",
            #            IDField(name="rowid", unique=True, primary_key=True))

            # init database instance for this class
            cls.database = Database()
            cls.database.contribute(cls)

            # populate cls.objects
            cls.objects = DataManager(cls)
Пример #6
0
    def __init__(self, **kw):
        # copy class base_fields to instanc:e
        self.fields = {}
        for name, field in self.__class__.base_fields.items():
            self.fields[name] = field.clone()

        # if there is some keyword-argument, that is not handled by the record, throw exception
        for key in kw:
            if key == "rowid":
                continue

            if not key in self.fields:
                raise DatabaseError(
                    "The field/keyword: '{}' was not found in the record".
                    format(key))

        # set this obj as parent for all fields
        for name, field in self.fields.items():
            field.parent = self

        from fields import ManyToOneRelation, OneToManyRelation, \
                OneToOneRelation, ManyToManyRelation

        # process each defined field
        self.rowid = None
        self.found_primary_key = False
        for k, v in kw.items():
            field = self.fields.get(k)

            # keep field using the primary_key flag and ensure its uniqueness
            if field is not None and field.primary_key:
                if not self.found_primary_key:
                    self.found_primary_key = (k, v)
                else:
                    raise DatabaseError("Found multiple 'primary_key' flagged fields. Inserting: {} Found: {}". \
                            format(k, str(self.found_primary_key)))

            # relation-field -> 1:N
            elif issubclass(field.__class__, OneToManyRelation):
                field.set(v)

            # relation-field -> N:1
            elif issubclass(field.__class__, ManyToOneRelation):
                #rid = v if isinstance(v, int) else v.rowid
                #field.set(field.related_record.objects.get(rowid=rid))
                field.set(v)

            # relation-field -> 1:1
            elif issubclass(field.__class__, OneToOneRelation):
                #rid = v if isinstance(v, int) else v.rowid
                #field.set(field.related_record.objects.get(rowid=rid))
                field.set(v)

            # relation-field -> N:M
            elif issubclass(field.__class__, ManyToManyRelation):
                raise DatabaseError("NOT IMPLEMENTED: ManyToManyRelation")

            # unique-identifier field
            # (overwritten by user-defined Field, if inside this branch)
            elif k == "rowid":
                if field is not None:
                    field.set(v)
                self.rowid = v

            # regular, all other fields
            else:
                field.set(v)
Пример #7
0
    def __init__(self, **kw):
        # copy class base_fields to instance
        self.fields = {}

        from fields import ManyToOneRelation, OneToOneRelation, \
                ManyToManyRelation, BaseFieldGroup

        for name, field in self.__class__.base_fields.items():
            self.fields[name] = field.clone()
            self.fields[name].name = name

        # check for a non-existing passwd keyword
        for key in kw:
            if key == "rowid":
                continue

            if not key in self.fields:
                raise DatabaseError("The field/keyword: '{}' was not found " + \
                                    "in the record".format(key))

        # set this obj as parent for all fields
        for name, field in self.fields.items():
            field.parent = self

        # 'dirty'-flag ... 'True' -> needs to be saved
        self.dirty = True

        # keyword assignment
        add_kw = {}
        for name in kw.keys():
            field = self.fields.get(name)
            if isinstance(field, BaseFieldGroup):
                for k in field.key2field.keys():
                    add_kw[name + "__" + k] = getattr(kw.get(name), k)
        kw.update(add_kw)

        # process each defined field
        self.rowid = None
        self.found_primary_key = False

        for k, v in kw.items():
            field = self.fields.get(k)
            # keep field using the primary_key flag and ensure its uniqueness
            if field is not None \
                    and hasattr(field, "primary_key") \
                    and field.primary_key:

                if not self.found_primary_key:
                    self.found_primary_key = (k, v)
                else:
                    raise DatabaseError("Found multiple 'primary_key' " + \
                            "flagged fields. Inserting: {} Found: {}". \
                            format(k, str(self.found_primary_key)))

            # handle index col
            elif k == "rowid":
                if field is not None:
                    field.set(v)
                self.rowid = v

            # regular, all other fields
            else:
                field.set(v)

        for k, v in self.fields.items():
            if isinstance(v, BaseFieldGroup):
                v.update_cls()