Task.map interaction with optional arguments

For mapped tasks with optional single value arguments is it intended to have to wrap the optional argument values with unmapped as shown below? It seems unintuitive to have to set the unmapping on the task when it can be invoked with or without .map. Also, the unmapped optional task parameter forces the task to be invoked with .map or it fails.

from typing import List
from prefect import task, flow
from prefect.utilities.annotations import unmapped

def mytask(x: int, y: int = unmapped(5)) -> int:
    return x + y

def myflow(c: int) -> List[int]:
    return mytask.map(list(range(c)))

if __name__ == "__main__":
    res = myflow(4)

Is there some specific question do you want to ask in this thread? The purpose of unmapped is to supply additional arguments to the map function which should not be mapped over. Without it you would only be able to call a task with the arguments that provide an iterable, no extra static arguments would be allowed.

Understood, the question is why do I have to put the unmapped in the @task / function definition for my example to work?

to provide non-mapped arguments, check those docs, it should make it clearer:

Yes I read that, it doesn’t cover this scenario where the task function definition has an optional argument with a default value. Let me contrast with how this works in v1 and maybe that helps clarify the question/issue.

from typing import List
from prefect import task, Flow, unmapped

# NOTE that unmapped(5) is not needed on the y optional input
# to make this work in v1
def mytask(x: int, y: int = 5) -> int: 
    return x + y

if __name__ == "__main__":
    with Flow("MyFlow") as flow:

    state = flow.run()

so you mean that the default value must still be explicitly passed, otherwise mapping fails? if so, this is more a candidate for a GitHub issue, feel free to create one

Yes, default must be explicitly passed or I have to apply unmapped on it at the task level as a workaround. I’ll open an issue on GH, thanks.