marshmallow icon indicating copy to clipboard operation
marshmallow copied to clipboard

[RFC] Add BigInt, SmallInt,... fields.

Open lafrech opened this issue 9 months ago • 3 comments

Originally in https://github.com/marshmallow-code/flask-smorest/pull/549.

One may add a range validator to every int field in their code base but that is cumbersome. Or subclass the Integer field to create a dedicated field, but it is a pity to do it in every code base if it can be done here.

Since this seems to be a common need, and the vocabulary seems to be shared across databases (https://www.postgresql.org/docs/current/datatype-numeric.html, https://learn.microsoft.com/fr-fr/sql/t-sql/data-types/int-bigint-smallint-and-tinyint-transact-sql), perhaps we could provide dedicated fields in marshmallow.

- BigInteger(Integer) -> Range(-2**63+1,2**63-1)
- SmallInteger(Integer) -> 2**8

I don't know how we'd call 2**32 Integer without breaking current Integer field.

Or we make this a parameter of Integer. But I think a dedicated class is nicer to use.

lafrech avatar Sep 11 '23 08:09 lafrech

Should I make a pull request for 64bit?

Code would be:

class MyBigInteger(ma.fields.Integer):
    """A 64bit signed integer field."""

    # gets merged with all parent classes
    default_error_messages: ClassVar = {"invalid_bigint": "Number not valid bigint."}

    def __init__(self, *, strict: bool = False, **kwargs):
        self.strict = strict
        super().__init__(**kwargs)
        # make sure the validator is first
        # will be used in flask-smorest by default unless there's another one validator
        self.validators.insert(0, ma.validate.Range(min=(-(2**63) + 1), max=(2**63 - 1)))
        # format is used in open-api apispec for nicer docs
        self.metadata["format"] = "int64"

ddorian avatar Oct 01 '23 14:10 ddorian

I'd rather we tackle all those fields at once. I like Big/SmallInteger but I'm short of ideas wrt the name of the Integer (2**32) field since Integer already exists and we don't mean to change it.

Or should we use Integer8, Integer32 and Integer64? I like the explicitness.

Regarding the implementation,

  • strict is set in parent class, no need to do it here.
  • format can be inferred from the class in apispec
  • not sure I understand the point about the order, I suppose this allows to set other validators that rely on the fact that this one passes (integer in allowed range), this makes sense to me

lafrech avatar Oct 01 '23 21:10 lafrech

I'd rather we tackle all those fields at once.

Much easier to get accepted for one at a time. And I had problem only with 64bit.

Or should we use Integer8, Integer32 and Integer64? I like the explicitness.

Yes.

strict is set in parent class, not need to do it here.

Agree.

format can be inferred from the class in apispec

Ok.

ddorian avatar Oct 02 '23 06:10 ddorian