Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Add a static factory with Generic Arguments #4421

Open
xenoterracide opened this issue Mar 24, 2025 · 2 comments
Open

Add a static factory with Generic Arguments #4421

xenoterracide opened this issue Mar 24, 2025 · 2 comments

Comments

@xenoterracide
Copy link

xenoterracide commented Mar 24, 2025

Arguments class is not Generic, and neither is of this probably cant be changed, but I'm thinking we could do cleaner, or at least more idiomatic than this.

  static class Clients implements ArgumentsProvider {

    @Override
    public Stream<? extends Arguments> provideArguments(ExtensionContext context) {
      return Stream.of(
        Arguments.of((Function<Integer, CommonCardAccountRepository>) CommonCardAccountRepositoryWebClientDefault::new)
      );
    }
  }

this at least would not require casting

  static class Clients implements ArgumentsProvider {

    @Override
    public Stream<? extends Arguments> provideArguments(ExtensionContext context) {
      return Stream.of(
        Arguments.generic<Function<Integer, CommonCardAccountRepository>(CommonCardAccountRepositoryWebClientDefault::new)
      );
    }
  }

maybe

  static class Clients implements ArgumentsProvider {

    @Override
    public Stream<? extends Arguments> provideArguments(ExtensionContext context) {
      return Arguments.stream<Function<Integer, CommonCardAccountRepository>(Arguments.generic(CommonCardAccountRepositoryWebClientDefault::new))
      );
    }
  }

Making Arguments itself generic would be better, but I'd bet we're past that since the API is marked stable. I think this would probably require a few method options which provide something like up to 5 generic parameters.

  static class Clients implements ArgumentsProvider {

    @Override
    public Stream<? extends Arguments<Function<Integer, CommonCardAccountRepository>> provideArguments(ExtensionContext context) {
      return Stream.of(
        Arguments.of(CommonCardAccountRepositoryWebClientDefault::new)
      );
    }
  }

mostly spitballing at this point, maybe someone else could come up with a better API. jupiter 5.10.5

@marcphilipp
Copy link
Member

Thanks for raising the issue! I agree that casting to generic types is not great.

We initially decided to avoid making Arguments generic, because we'd need a variant for each number of arguments and when consuming we're using reflection anyway which only wants an Object[].

A common pattern I've seen is to use a Java record for this:

@Override
public Stream<? extends Arguments> provideArguments(ExtensionContext context) {
  return Stream.of(
    Arguments.of(new Data(CommonCardAccountRepositoryWebClientDefault::new))
  );
}

record Data(Function<Integer, CommonCardAccountRepository> function) {
}

That has the added benefit of ensuring that all argument sets use the same types.

Is that something you've tried (assuming you can use Java 16+)?

@xenoterracide
Copy link
Author

No, but that feels like a waste for 1-2 generic arguments. I suppose I could see it if you get beyond that, and certainly if you get beyond the recommended 4 max arguments.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

No branches or pull requests

2 participants