0

I would like to rewrite this function using streams if possible.

public void onTransfer(TransferEvent event) {

    StringBuilder builder = new StringBuilder();
    for (Object item : event.getItems()) {
        Permission perm = Permission.valueOf((String) item);

        try {
            if (event.isAdd()) {
                currentRole.add(perm);
            } else {
                currentRole.remove(perm);
            }
        } catch (Exception e) {
            addErrorMessage("", e.getLocalizedMessage());
            LOGGER.error(e.getMessage(), e);
        }
        builder.append(perm.name()).append(";");
    }

    addMessage("", "Transfered permissions " + builder.toString() + " from/to role :" + currentRole.getName());
}

Thank you in advance!

Naman
  • 27,789
  • 26
  • 218
  • 353
user5918
  • 13
  • 3
  • 5
    Why? This task is not really suitable for streams, having side effects. – RealSkeptic Nov 03 '20 at 12:31
  • It's an excercise for me given by my employer. I should either use streams or lambda – user5918 Nov 03 '20 at 13:12
  • Whilst fully agreeing that this method has side effects and therefore not really suited to the use of streams, I would see if me IDE would perhaps offer a refactor of the `for` loop to a `stream.forEach`. It would meet youre employers criteria I believe and depending on your taste it might be considered more readable. Though you might also want to extract the logic inside the loop to a private method. – Gavin Nov 03 '20 at 13:19
  • Can you please give me an example? :) – user5918 Nov 03 '20 at 13:35

1 Answers1

0

Rewriting this to stream-functions would look like this:

event.getItems().stream()
    .map(item -> Permission.valueOf((String) item))
    .forEach(perm -> {try-clause})
addMessage(event.getItems().stream()
    .map(item -> Permission.valueOf((String) item).name())
    .collect(Collectors.joining(";", "Transfered permissions ", " from/to role :" + currentRole.getName()));
MDK
  • 499
  • 3
  • 14
  • Note this could not get properly tested without all the other classes. – MDK Nov 03 '20 at 14:19
  • Thank you! Is there a way doing it without peek or is this the only way? – user5918 Nov 03 '20 at 14:46
  • Thanks for pointing that out @RealSkeptic, I forgot about that issue. I now corrected it to a better approach. Reference: https://stackoverflow.com/questions/33635717/in-java-streams-is-peek-really-only-for-debugging – MDK Nov 03 '20 at 15:16
  • There is someting missing, after transfered permission there also needs to be included the + builder.toString() + like above inside collectors joining. I fixed it myself thanks for the rest :) – user5918 Nov 04 '20 at 11:44
  • The collect operation should correctly replace your stringbuilder though, concatenating all names seperated by ;. If I made a mistake please edit the answer so future readers get the correct solution. – MDK Nov 04 '20 at 11:49