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

Entity#getScoreboardTags directly exposes the Set<String> #11296

Open
Machine-Maker opened this issue Aug 19, 2024 · 3 comments
Open

Entity#getScoreboardTags directly exposes the Set<String> #11296

Machine-Maker opened this issue Aug 19, 2024 · 3 comments
Labels
good first issue Simple bug fix or feature which would be a good first PR for someone new to the project status: accepted Disputed bug is accepted as valid or Feature accepted as desired to be added. type: bug Something doesn't work as it was intended to.

Comments

@Machine-Maker
Copy link
Member

An entity will only load 1024 scoreboard tags from it's NBT, and the addTag methods on nms.Entity automatically check this and return false if it's over 1024. These methods are directly called by the API addScoreboardTag method. The problem is, the API also has getScoreboardTags which directly exposes the underlying set, no copy, no unmodifiable wrapper, nothing. So a plugin can just add strings to that set to add over 1024 tags which are then saved, and lost on a reload of the entity.

Either we copy the set to make it a mutable copy or wrap it in an unmodifiable wrapper or we do an immutable copy.

@Machine-Maker Machine-Maker added type: bug Something doesn't work as it was intended to. status: accepted Disputed bug is accepted as valid or Feature accepted as desired to be added. labels Aug 19, 2024
@imDaniX
Copy link

imDaniX commented Aug 19, 2024

Should this be unmodifiable/a copy tho? The javadoc sentence *Entities can have no more than 1024 tags. seems to imply that you can add tags.
I feel like this should be rather return a set that delegates everything to the underlying set, but overrides add and addAll methods, like

@Override
public boolean add(String tag) {
    return entity.addScoreboardTag(tag);
}

@Override
public boolean addAll(@NotNull Collection<? extends String> tags) {
    boolean edited = false;
    for (String tag : tags) {
        edited = entity.addScoreboardTag(tag) || edited;
    }
    return edited;
}

@Machine-Maker
Copy link
Member Author

Not super opposed to that solution. But I'm not sure that the sentence you quoted does imply that. It just seems unlikely that was the intention when there is also an "add" method right next to the getScoreboardTags method. In general I don't think its good to have add/remove methods as well as expose a mutable set which can just take the place of those add/remove methods.

@lynxplay
Copy link
Contributor

I agree with machine that the javadocs are very open to interpretation in regards to the returned set being mutable.
However, this API has existed for so long and is an upstream API as well, that we obviously cannot just return an unmodifiable
set.

I think we'd indeed be best of to wrap the returned set in a form of delegating wrapper.
We can already start potentially printing nags that this behaviour is strongly discouraged and "deprecated for removal".
Not that we can remove it until hardfork, but a heads up warning via nag may be a useful addition to danix's suggestion.

@Machine-Maker Machine-Maker added the good first issue Simple bug fix or feature which would be a good first PR for someone new to the project label Sep 8, 2024
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
good first issue Simple bug fix or feature which would be a good first PR for someone new to the project status: accepted Disputed bug is accepted as valid or Feature accepted as desired to be added. type: bug Something doesn't work as it was intended to.
Projects
Status: ✅ Accepted
Development

No branches or pull requests

3 participants