Re-create & test number converter

pull/118/head
stijndcl 2022-07-01 12:43:41 +02:00
parent fd72bb1774
commit 96916d2abd
4 changed files with 92 additions and 0 deletions

View File

@ -0,0 +1,42 @@
import math
from typing import Optional
def abbreviated_number(argument: str) -> int:
"""Custom converter to allow numbers to be abbreviated
Examples:
515k
4m
"""
if not argument:
raise ValueError
if argument.isdecimal():
return int(argument)
units = {"k": 3, "m": 6, "b": 9, "t": 12}
# Get the unit if there is one, then chop it off
unit: Optional[str] = None
if not argument[-1].isdigit():
if argument[-1].lower() not in units:
raise ValueError
unit = argument[-1].lower()
argument = argument[:-1]
# [int][unit]
if "." not in argument and unit is not None:
return int(argument) * (10 ** units.get(unit))
# [float][unit]
if "." in argument:
# Floats themselves are not supported
if unit is None:
raise ValueError
as_float = float(argument)
return math.floor(as_float * (10 ** units.get(unit)))
# Unparseable
raise ValueError

View File

@ -0,0 +1,50 @@
import pytest
from didier.utils.discord.converters import numbers
def test_abbreviated_int():
"""Test abbreviated_number for a regular int"""
assert numbers.abbreviated_number("500") == 500
def test_abbreviated_float_errors():
"""Test abbreviated_number for a float"""
with pytest.raises(ValueError):
numbers.abbreviated_number("5.4")
def test_abbreviated_int_unit():
"""Test abbreviated_number for an int combined with a unit"""
assert numbers.abbreviated_number("20k") == 20000
def test_abbreviated_int_unknown_unit():
"""Test abbreviated_number for an int combined with an unknown unit"""
with pytest.raises(ValueError):
numbers.abbreviated_number("20p")
def test_abbreviated_float_unit():
"""Test abbreviated_number for a float combined with a unit"""
assert numbers.abbreviated_number("20.5k") == 20500
def test_abbreviated_float_unknown_unit():
"""Test abbreviated_number for a float combined with an unknown unit"""
with pytest.raises(ValueError):
numbers.abbreviated_number("20.5p")
def test_abbreviated_no_number():
"""Test abbreviated_number for unparseable content"""
with pytest.raises(ValueError):
numbers.abbreviated_number("didier")
def test_abbreviated_float_floors():
"""Test abbreviated_number for a float that is longer than the unit
Example:
5.3k is 5300, but 5.3001k is 5300.1
"""
assert numbers.abbreviated_number("5.3001k") == 5300