#paper

32998 messages · Page 33 of 33 (latest)

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

When a chunk is unloaded and ChunkUnloadEvent#setSaveChunk(false) is called, entities should not be saved.

Observed/Actual behavior

I noticed when the chunk unloads, and reloads... the previous entities are there, along with a new batch of entities.
For example im standing in a chunk that spawned 4 pigs.
When I log out/in... there's a new batch of pigs along with the pigs from the last chunk generation. Each time I do this, more and more piggies.

<img width="966" height="620" alt="Image" src="https://github.com/user-attachments/assets/f0199c3c-42be-468f-b68f-f159797603fb" />

Steps/models to reproduce

simple listener:

@EventHandler
public void onChunkUnload(ChunkUnloadEvent event) {
    event.setSaveChunk(false);
}

Plugin and Datapack List

[09:41:21 INFO]: ℹ Server Plugins (10):
[09:41:21 INFO]: Paper Plugins (5):
[09:41:21 INFO]: - CorePlugin, SkBee, SkBriggy, SkNMS, StressTestBots
[09:41:21 INFO]: Bukkit Plugins (5):
[09:41:21 INFO]:...

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

When a player is teleported to a different world during the PlayerJoinEvent, settings like the worldborder should be correctly updated to the client for the target world.

Observed/Actual behavior

There is a desynchronization between the client and the server regarding the world border. When a player logs in and gets teleported to a different world on join, the server correctly updates the border internally, but the client only updates partially.

From the player's perspective, the world border center and size appears to be the old targeted world's one, producing issue like making it seem as though the player is outside the border or running against an invisible wall. Running /worldborder center outputs the correct coordinates, confirming the server recognizes the right center.

Switching to a different world and returning resolves the desynchronization completely.

Steps/models to reproduce

Prepare a server with at least two different worlds (e.g., w...

#

its because this got reverted

<img width="2683" height="521" alt="Image" src="https://github.com/user-attachments/assets/a72dcd13-bcfc-4746-8ae3-82f72f15bcf4" />

And issue is PlayerList#placeNewPlayer

        // calls PlayerJoinEvent
        ....
        player.sentListPacket = true;
        player.suppressTrackerForLogin = false; // Paper - Fire PlayerJoinEvent when Player is actually ready
        ((ServerLevel)player.level()).getChunkSource().chunkMap.addEntity(player); // Paper - Fire PlayerJoinEvent when Player is actually ready; track entity now
        // CraftBukkit end

        //player.refreshEntityData(player); // CraftBukkit - BungeeCord#2321, send complete data to self on spawn // Paper - THIS IS NOT NEEDED ANYMORE
this--->this.sendLevelInfo(player, serverLevel);

        // CraftBukkit start - Only add if the player wasn't moved in the event
        if (player.level() == serverLevel && !serverLevel.players().contains(player)) {
            serverLevel.addNewPlay```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

Yes.
So I wrote a datapack, which pulls my world's lowest Y to -256.
After many attempts and asking a few AIs to help me with figuring out lava, lava kept pooling around -54Y.
Turns out Mojang hardcoded this value.
I reported it as a bug, and it was closed saying "request a feature, this isn't a bug"
Which I find funny, they give us the control in a datapack to go down to -2032Y, but our caves will be full of lava.
My bug MC-307994

Someone commented stating another bug MC-237017
This one (same issue as mine) remains open, so that's good news that its not closed, but bad news is in 5 years it hasn't been fixed.

Describe the solution you'd like.

In net.minecraft.world.level.levelgen.NoiseBasedChunkGenerator:

<img width="1020" height="237" alt="Image" src="https://github.com/user-attachments/assets/3bc715c0-b04d-45c7-bb2e-e7d3737a74b0" />

This is the hardcoded value. Id love to see a config option for this, or another alternative...

rustic folioBOT
#

Minecraft gives us the ability in data packs to modify the min Y of a world.
Unfortunately when dropping the Y to a lower value, caves with always be flooded with lava.
This is due to a hardcoded lava level.

I reported it as a bug, and it was closed saying "request a feature, this isn't a bug"
Which I find funny, they give us the control in a datapack to go down to -2032Y, but our caves will be full of lava.
My bug MC-307994

Someone commented stating another bug MC-237017
This one (same issue as mine) remains open, so that's good news that it's not closed, but bad news is in 5 years it hasn't been fixed. It's also confirmed.

Rather than hardcoding the lava level at a strict -54, this PR aims to take the min Y of the noise settings and add 10.
So min Y being -64, it still results in -54.
If a datapack (such as mine) drops it to -256, the result will be -246.
I have tested this on my own server with said datapack, and works perfectly.

Ref issue #13878...

rustic folioBOT
#

This really feels like this falls into the annoying "maybe makes sense but I'm not entirely sure it should be our job to make this, especially as we have no idea who might be surprised by it"

I totally get what you mean, I've just run out of ideas on how to make this work.
Only alternative I currently have is my own patch for myself.
I just do wonder how many others have run into this issue and it's gone unmentioned.

I can't think of any negative side effects from this, nor any alternative, but I'm all ears.

#

negative side effects would be a datapack gen setting applying in a way it didn't in the past, which will impact generation for new chunks, etc

Yeah that's fair.

Let's use this scenario (before this PR).
Say I wrote a datapack that pulls Y down to -128.
Old chunk is going to be -64
New chunk is going to be -128
Lava is going to flood the new chunk's caves from -54 downwards.
No one can use new deeper caves. Total waste ... sad face.

Post PR:
Same as above, but caves won't be flooded, player will be able to go down to newer, lower levels, happy face!
Only pitfall is players will be able to jump out of the new chunk since the old chunk didn't go down to that new level.

Datapacks that alter things like this typically shouldn't be put into old worlds, but we all know things happen.

I really wish Mojang didn't hardcode this in the first place. its so odd its not part of the datapack like everything else.

rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] New branch created: feature/vineflower-12.0.0
rustic folioBOT
#

Before this change, the Bukkit ItemStack passed to the event is constructed from a Bukkit Material, which relies on the Bukkit mapping from blocks to items being the same as the Minecraft mapping from blocks to items.

However, it is not the same.
For example, new ItemStack(Material.POTATOES) does not give an ItemStack of type Material.POTATO as it should.
So a flower pot block created as new FlowerPotBlock(Blocks.POTATOES, properties) will crash the server.

After this change, the Bukkit ItemStack passed to the event is constructed from the Minecraft ItemStack, which relies on the Minecraft mapping from blocks to items being correct.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

This is a WAI since custom spear allow to dismount without doing damage/knockback so it's not related at all.

Hello, I don’t quite understand this situation.

Some servers use boats or minecarts to display mobs or build mob farms. Even when players do not have permission to attack entities, they can still use spear charges to dismount mobs from vehicles.

Is there currently any proper way to prevent this behavior? Or would it be better to create a feature request for something like a SpearChargeDismountEvent?

rustic folioBOT
#

Is your feature request related to a problem?

When the attack event caused by SpearCharge is cancelled, the entity will still dismount from boat and minecart.
https://github.com/PaperMC/Paper/issues/13583

Many players trap various mobs inside minecarts and boats for display purposes, and some mob farms also rely on this mechanic. However, SpearCharge can now bypass protection in these areas; while it cannot deal damage to the mobs, it is able to force them to dismount.

Describe the solution you'd like.

Added SpearChargeDismountEvent, which provides access to the SpearCharge attacker. Region protection plugins can perform fine-grained permission checks to allow or prevent the dismount event

Describe alternatives you've considered.

Or make EntityDismountEvent able to capture the attacker, if an attacker exists.

Other

No response

rustic folioBOT
#

Expected behavior

EntityDamageByEntityEvent should getAttackCooldown correctly

Observed/Actual behavior

Attack with hand is always 0.1, and attack with sword is always 0.039999995

Steps/models to reproduce

@EventHandler
public static void onEntityDamageByEntityEvent(EntityDamageByEntityEvent event) {
    if (event.getDamager() instanceof Player player) print(player.getAttackCooldown());
}

Plugin and Datapack List

test plugin only

Paper version

Paper 26.1.2-63
since Paper 26.1.2-55 after #13856

Other

No response

rustic folioBOT
#

Expected behavior

Bukkit.getBukkitVersion() and Server.getBukkitVersion() functions are supposed to return the current version of Bukkit API which is implemented by server software (here Paper-server). For instance 26.1.2 or 26.1.2-SNAPSHOT or 26.1.2-R0.1-SNAPSHOT.

In all former versions (before 26.1.2), it worked perfectly. Example: 1.19.4-R0.1-SNAPSHOT

Observed/Actual behavior

For 26.1.2 servers, the version number returned is the server one: 26.1.2.build.63-stable instead of the API one.

Steps/models to reproduce

Two possibilities:

  • Invoke the Bukkit.getBukkitVersion() in a plugin
  • Type /version in the console. The Bukkit API version number is shown after Implementing API version string.

Plugin and Datapack List

BlockLocker, CMILib, DecentHolograms, Essentials, EssentialsAntiBuild, EssentialsChat, EssentialsSpawn, GroupManager, Multiverse-Core, Multiverse-Inventories, Multiverse-Portals, PlaceholderAPI, pvparena, Residence, Vault, WorldEdit, WorldGuard

##...

#

That means developing a specific way to parse it and compare it if I need to provide specific version features.

You can use https://jd.papermc.io/paper/26.1.2/io/papermc/paper/ServerBuildInfo.html#minecraftVersionId() or https://jd.papermc.io/paper/26.1.2/org/bukkit/Bukkit.html#getMinecraftVersion() for alternative representation if you want, that would be kept with what mojang is providing

#

That means developing a specific way to parse it and compare it if I need to provide specific version features.

You can use https://jd.papermc.io/paper/26.1.2/io/papermc/paper/ServerBuildInfo.html#minecraftVersionId() or https://jd.papermc.io/paper/26.1.2/org/bukkit/Bukkit.html#getMinecraftVersion() for alternative representation if you want, that would be kept with what mojang is providing

Both methods are not available in common Bukkit API, for instance they don't exist in Spigot.

rustic folioBOT
#

There isn't a bukkit API version and hasn't for a decade, the API and the Server are versioned together, we no longer use SNAPSHOT releases; We're not semver compliant and that was never something that was garaunteed

During many years Spigot and Paper returned the same result when a Bukkit API method was called. This was useful and make possible interoperability between server software. That's how an API is supposed to work.
Now, if it's a design choice and not a bug, I respect that. I was here to report what I thought was an issue, not to impose anything.

rustic folioBOT
#

Leaving this longer messages for those interested in more details:

During many years Spigot and Paper returned the same result when a Bukkit API method was called.

Bukkit died in 2014.

For years, Paper was based on Spigot, so it did whatever Spigot did.

When Paper split from Spigot at 1.21.4, it became possible for Spigot and Paper to have different classes/methods entirely or to have same-named methods return different values. If a developer wishes to support the 95+% of modern servers running Paper and also the under 5% of servers on Spigot, they should be writing code to handle each, because there are deviations (sometimes significant!).

Minecraft 26.1 was a major versioning shift in MC, making it a great time to also properly adjust the versioning values you get from the API:
Considering the last R1.0 was on MC 1.6.4, dropping the R0.1 bit is reasonable. Including build numbers is great, because sometimes an API method appears later on than the first working builds, so a pl...

rustic folioBOT
#

That event feels overly specific, but I don't mind having a generic EntityStabEvent with toggles for damage, knockback and dismount along the attacker. Maybe something like this:

if (!event.getAttacker().hasPermission("plugin.dismount")) {
event.getActions().remove(Action.DISMOUNT);
}

that can be a thing for EntityLungeEvent or that event its to early?

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

That event feels overly specific, but I don't mind having a generic EntityStabEvent with toggles for damage, knockback and dismount along the attacker. Maybe something like this:

if (!event.getAttacker().hasPermission("plugin.dismount")) {
event.getActions().remove(Action.DISMOUNT);
}

So long as I can obtain the attacker, I don't mind what the event is called.^_^

rustic folioBOT
rustic folioBOT
#

Using the following listener, the logged loot table currently matches the default loot table of the entity, not the actual loot table used:

    @EventHandler
    public void onEntityDeath(EntityDeathEvent event) {
        if (event.getEntity() instanceof Mob mob) {
            this.getSLF4JLogger().warn("Entity {} died with loot table: {}", mob.getName(), mob.getLootTable());
        }
    }

During my test, the Pig I modified did drop rotten flesh despite the console printing entities/pig loot table

[02:11:45 INFO]: roro1506_HD issued server command: /data merge entity 62185aec-e858-4945-a41a-6e21107085b7 {DeathLootTable:"minecraft:entities/zombie"}
[02:11:45 INFO]: [roro1506_HD: Modified entity data of Pig]
[02:11:47 WARN]: [Paper-Test-Plugin] Entity Pig died with loot table: minecraft:entities/pig

This PR fixes this issue

[16:12:32 INFO]: roro1506_HD issued server command: /data merge entity c3c71d92-632f-49d3-a682-fd062b85f884 {DeathLootTable:"minecra```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

No WARM

Observed/Actual behavior

WARNING: A terminally deprecated method in sun.misc.Unsafe has been called
WARNING: sun.misc.Unsafe::objectFieldOffset has been called by org.joml.MemUtil$MemUtilUnsafe (file:/X:/MinecraftServer/libraries/org/joml/joml/1.10.8/joml-1.10.8.jar)
WARNING: Please consider reporting this to the maintainers of class org.joml.MemUtil$MemUtilUnsafe
WARNING: sun.misc.Unsafe::objectFieldOffset will be removed in a future release

Steps/models to reproduce

Start Server
Use JDK 25

Plugin and Datapack List

No have

Paper version

ver
[18:46:07 INFO]: Checking version, please wait...
[18:46:08 INFO]: This server is running Paper version 1.21.11-132-ver/1.21.11@c5eb079 (2026-05-11T11:43:09Z) (Implementing API version 1.21.11-R0.1-SNAPSHOT)
You are running the latest version
Previous version: 1.21.11-131-6d5b910 (MC: 1.21.11)

Other

Can you are add this update to papermc 1.21.11?
Can you are Fix this?

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

No errors in the console

Observed/Actual behavior

I'm just flying around the world and this error appears in the console:

<img width="1090" height="330" alt="Image" src="https://github.com/user-attachments/assets/0fb12b60-7f4e-4f18-8e47-8ff148c20384" />

Steps/models to reproduce

  1. Enable Anti-Xray
  2. Join the server
  3. Load chunks
  4. View the console

Plugin and Datapack List

[03:25:10 INFO]: ℹ Server Plugins (61):
[03:25:10 INFO]: Paper Plugins (1):
[03:25:10 INFO]: - PlugManX
[03:25:10 INFO]: Bukkit Plugins (60):
[03:25:10 INFO]: - AntiHealthIndicator, AuraSkills, AutoMessage, BanItem, BigDoors, BookExploitFix, BreweryX, ChatSpy, Citizens, CommandAPI
[03:25:10 INFO]: CoreProtect, CustomCrafting, DeluxeMenus, dtlTraders, dynmap, Dynmap-Towny, EasyPayments, Essentials, EssentialsProtect, EssentialsSpawn
[03:25:10 INFO]: FastAsyncWorldEdit, GoldEconomy, GSit, HeadDatabase, ImageFrame, Interactions, Kostyl, KostylTWO, LicuhaDe, LiteBans
[03:2...

rustic folioBOT
#

The issue here is that world types aren't a thing anymore, these are just templates, effectively; said template used for the end/nether and the others are applied to the overworld.

Not really sure I like the surfacing of this stuff as a result of that, the underlying concept of a world type no longer exists, this is just trying to marry an outdated deprecated concept with it's replacement cousin which works differently in a sense

rustic folioBOT
#

Expected behavior

The firework should always use the data from the new item.

Observed/Actual behavior

The old firework data is retained. Note that this only occurs when updating the firework's item, i.e. setting an item on a firework that already has an item.

Steps/models to reproduce

Use Firework#setItem on a firework entity that already has an item set. Can be done at any time during its life.

Here's a small example that should summon a green firework, but summons a red one instead.

ItemStack first = ItemStack.of(Material.FIREWORK_ROCKET);
first.setData(DataComponentTypes.FIREWORKS, Fireworks.fireworks()
        .addEffect(FireworkEffect.builder()
        .withColor(Color.RED)
        .build()));

ItemStack second = ItemStack.of(Material.FIREWORK_ROCKET);
second.setData(DataComponentTypes.FIREWORKS, Fireworks.fireworks()
        .addEffect(FireworkEffect.builder()
        .withColor(Color.GREEN)
        .build()));

location.getWorld().spawn(location, Firework.```...
rustic folioBOT
rustic folioBOT
#

This PR closes https://github.com/PaperMC/Paper/issues/13890 and also handle a few things i notice when check the class...

  • setItem set the item but also use any previous ItemMeta for set the item again, the PR just remove the use of ItemMeta in setItem because currently its not necesary (thanks Components)
  • the helper method applyFireworkEffect was removed because that logic its only necesary for setFireworkMeta
  • a cleanup of comments and imports

I make a few tests for this changes...

The issue reported where the second item was ignored

final Location location = player.getLocation().clone().add(0, 1, 0);
ItemStack first = ItemStack.of(Material.FIREWORK_ROCKET);
first.setData(DataComponentTypes.FIREWORKS, Fireworks.fireworks()
    .addEffect(FireworkEffect.builder()
        .withColor(Color.RED)
        .build()));

ItemStack second = ItemStack.of(Material.FIREWORK_ROCKET);
second.setData(DataComponentTypes.FIREWORKS, Fireworks.fireworks()
    .addEffect(F```...
#

I would argue then that this is more a temporary solution for people to be able to detect the different types and being able to create CAVES, FLOATING_ISLANDS and DEBUG from WorldCreator while a better more improved system can be made

I've made commits now to add a method to get the key and re-deprecated the getWorldType(), but I think the added world types should be kept for creating new worlds until said better system is made

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Related to a comment this PR set obsolete the use of PotionMeta in Potion entities, also remove the use of them in the "Craft" classes because are not necesary.

I test this PR with the follow cases...

For use a ItemMeta and set to the potion

final Location location = player.getLocation().clone().add(0, 1, 0);
ItemStack first = ItemStack.of(Material.LINGERING_POTION);
first.editMeta(PotionMeta.class, meta -> {
    meta.addCustomEffect(new PotionEffect(PotionEffectType.REGENERATION, 10 * 20, 10), true);
});

final LingeringPotion entitySpawned = location.getWorld().spawn(location, LingeringPotion.class, entity -> {
    entity.setPotionMeta(((PotionMeta) first.getItemMeta()));
});

PotionMeta meta = entitySpawned.getPotionMeta();
player.sendMessage(meta.toString());

Set the ItemMeta but use the item

final Location location = player.getLocation().clone().add(0, 1, 0);
ItemStack first = ItemStack.of(Material.LINGERING_POTION);
first.editMeta(PotionMeta.```...
#

Expected behavior

users not being able to set

level-name=

and it leading to creation of a world with empty string as a name, leading to plugin errors, because there was an assumption that world name is not an empty string.

Observed/Actual behavior

level-name=

results in creation of the world in the server root directory.

level-name=../

will attempt to create the world in the parent directory and

level-name=/home/someuser/world
will create it on the absolute path

all cases are likely to break plugin configs relying on the world name

### Steps/models to reproduce

1. start a clean server
2. set `level-name=` in server-properties
3. see all the world files dumped in the server root directory

### Plugin and Datapack List

n/a

### Paper version

n/a (present in vanilla, [bug report](https://report.bugs.mojang.com/servicedesk/customer/portal/2/MC-308240))

### Other

_No response_
rustic folioBOT
rustic folioBOT
#

Back here because I found the Statistics api. Statistics can be edited using an OfflinePlayer instance. This might be due to their api being a bit more exposed than the player.dat file, but it just creates an empty file for them if they didn't have one already. This makes me think the best implementation for this is to just create the .dat file when a dev edits a player's PDC. Like with stats, the write operation can happen when a value is changed.

rustic folioBOT
#

Stack trace

https://api.mclo.gs/1/raw/HMf1QmP

Plugin and Datapack List

my own plugin

Actions to reproduce (if known)

I wrote these

builder.base(DialogBase.builder(Component.text("选择存档", NamedTextColor.WHITE))
                            .canCloseWithEscape(false)
                            .body(List.of(
//                                    DialogBody.plainMessage(Component.text("这是一条测试信息")),
//                                    DialogBody.plainMessage(Component.text("这是一条测试信息2"))

                                    DialogBody.item(new ItemStack(Material.DIAMOND))
//                                            .description(DialogBody.plainMessage(Component.text("钻石一个")))
//                                            .height(1)
//                                            .showDecorations(true)
//                                            .width(1)
//                                            .showTooltip(true)
                                            .build()```...
rustic folioBOT
rustic folioBOT
#

Expected behavior

A PlayerInteractEvent with action = LEFT_CLICK_AIR must be triggered

Observed/Actual behavior

PlayerInteractEvent is not being triggered

Steps/models to reproduce

/attribute @p minecraft:entity_interaction_range base set 10
https://youtu.be/NhFysJaVHiA

Plugin and Datapack List

none

Paper version

the second-to-last one; it doesn't make sense

Other

This can be fixed by adding the same check as in hitEntity, but replacing entity with block and entityInteractionRange with blockInteractionRange.

else if (gameType != GameType.CREATIVE && result.getHitBlock() != null && origin.toVector().distanceSquared(result.getHitPosition()) > this.player.blockInteractionRange() * this.player.blockInteractionRange()) {
                CraftEventFactory.callPlayerInteractEvent(this.player, Action.LEFT_CLICK_AIR, this.player.getInventory().getSelectedItem(), InteractionHand.MAIN_HAND);
            }
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

The server should automatically convert names for keys regarding feature seeds in paper-world.yml configurations in each world folder from their 1.21.11 format to their 26.1.2 format, respectively.

Observed/Actual behavior

When upgrading the server from 1.21.11 to 26.1.2, some feature seeds can not be deserialized from the paper-world configuration file because the name of the key of the feature seed is different across the versions. This causes an error like this to be shown for each feature seed that can't be deserialized:

[14:59:04] [Server thread/ERROR]: [MapSerializer] Could not deserialize key minecraft:pale_forest_flowers into net.minecraft.core.Holder<net.minecraft.world.level.levelgen.feature.ConfiguredFeature<?, ?>> at [feature-seeds, features]: Missing holder in ResourceKey[minecraft:root / minecraft:worldgen/configured_feature] with key ResourceKey[minecraft:worldgen/configured_feature / minecraft:pale_forest_flowers]

Steps/models to reproduce...

rustic folioBOT
rustic folioBOT
#

I feel your pain. After spending a lot of time digging into this, it's clear that the "bridge" the developers mentioned in the commit has indeed collapsed for all of us.

Since it seems we're left to "cross this bridge" on our own without any one-click fix or config toggle from the server side, I've found a workaround. For those of you using mineflayer, you can simulate the missing epsilon by slightly adjusting the client-side physics.

Just add this to your bot's spawn/init logic:


if (bot.physics) {
  bot.physics.playerHalfWidth = 0.302; // Restores the tiny gap needed to jump
}

It's a "client-side band-aid" for a "server-side wound," but it works. Until (or if) the devs decide to prioritize our experience over "pixel-perfect" collisions, this is the way.

#

Just a heads-up for everyone implementing this workaround:

If the Paper devs eventually decide to revert these changes and restore the epsilon, this client-side fix might cause slight "over-padding" (making the bot feel slightly wider than normal), which could potentially interfere with very tight navigation.

To keep your code maintainable, I suggest making this a configurable toggle in your bot's settings rather than a hardcoded value:

const usePaperCollisionFix = true; // Set to false if the server is updated/fixed

if (bot.physics) {
  bot.physics.playerHalfWidth = usePaperCollisionFix ? 0.302 : 0.3;
}

This way, you can quickly switch back to vanilla physics without hunting through your code if the server-side "improvement" is ever undone.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

I am having a similar issue with the following stack trace:

`---- Minecraft Crash Report ----
// There are four lights!

Time: 2026-05-21 18:19:38
Description: Exception in server tick loop

java.lang.RuntimeException: Failed to migrate world storage for world_nether
at io.papermc.paper.world.PaperWorldLoader.getWorldInfoAndData(PaperWorldLoader.java:65)
at io.papermc.paper.world.PaperWorldLoader.loadInitialWorld(PaperWorldLoader.java:150)
at io.papermc.paper.world.PaperWorldLoader.loadInitialWorlds(PaperWorldLoader.java:139)
at net.minecraft.server.MinecraftServer.loadLevel(MinecraftServer.java:650)
at net.minecraft.server.dedicated.DedicatedServer.initServer(DedicatedServer.java:382)
at net.minecraft.server.MinecraftServer.runServer(MinecraftServer.java:1301)
at net.minecraft.server.MinecraftServer.lambda$spin$0(MinecraftServer.java:304)
at java.base/java.lang.Thread.run(Thread.java:1474)
Caused by: java.io.IOException: Refusing to overwrite existing migrated file ./world/dim`...

rustic folioBOT
#

i find myself in need of an event like this but for a different reason, im building a progression system and would have liked to grant skill xp when a player repaired items in an anvil. Using InventoryClickEvent as said above is very unreliable (lets say the bottom inventory cant hold the item and the click type is shift click, i would need to test the entire inventory, for example) and has the possibility for false flags. a dedicated use event would be really nice.

PrepareAnvilEvent can't be used for this either since it only gets fired when the anvil recalculates stuff (at which point the result slots are empty if the anvil is used)

rustic folioBOT
#

Is your feature request related to a problem?

related to #13575

The grindstone and the anvil are the only workbenches who don't have a 'use' event related to their 'PrepareResultEvent' event.
e.g. PrepareSmithingEvent has SmithItemEvent, PrepareItemEnchantEvent has EnchantItemEvent, etc.

I require this functionality to be able to award skill xp for a progression system, for example.

Describe the solution you'd like.

Add GrindstoneItemEvent, (and AnvilUseEvent #13575), so that these actions can be properly detected,
or a more generic CompleteResultEvent, that would apply to all PrepareResultEvent events, when a result is completed.

Describe alternatives you've considered.

Listening to the InventoryClickEvent, but this requires hacky prediction of whether the item will actually leave the result slot.

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] branch deleted: feature/vineflower-12.0.0
rustic folioBOT
rustic folioBOT
#

I am unable to reproduce any of the behaviors you've mentioned, and since you also have not provided any other information than that there's really nothing we can do here. What you're describing does sound like what some naive lag "fixing" plugins might cause, but you claim you're only running essentials, so, yeah

#

Wouldn't this just be addRotation? Which, fair addition, I am just not very happy with the method name and parameters, they look to be copying internals one to one and seem very clunky.

//edit: Might not have said this nicely, there is obviously a different in the method as ServerPlayer makes use of those booleans to send the relative update packet instead. This is purely about naming of the API method.

if renamed to addRotation, the relative parameters will look more confusing, or you mean method like addRotation(yaw, pitch)?
I'd prefer just keep it. I added a note, which may be better

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

The key that the server says cannot be deserialized is found in the paper-world.yml config before upgrading, and disappears after upgrading, so it is correct that they are getting removed. However, upon checking the paper-world.yml after upgrading, I found many keys with similar names to the ones that got removed, many of which just have the word "patch_" removed from the beginning of the key (ex: minecraft:patch_pumpkin -> minecraft:pumpkin). I cannot say for certain that the old and the new keys with similar names are used for the same thing when generating the world, but if they are, Im not sure changing feature seeds is healthy for the world...

Also, I counted 25 keys that could not be deserialized and got removed, and the server only regenerated 22 keys after the 25 keys got removed, so three keys were completely removed from the config

rustic folioBOT
#

The past issue was marked as WAI as the error is kinda expected when stuff doesn't miss, there isn't any real means of automating the upgrades of this stuff too well, so it kinda falls by the wayside; That stuff is all backed off of Mojang's registries, and given that this is all basically generation stuff which doesn't get serialised, there is no migration logic inside of vanilla at all, and nothing we have to hook.

rustic folioBOT
#

Is your feature request related to a problem?

I currently have 27 worlds loaded on my Paper instance, but aside from the three main worlds, the rest are archive worlds in past 10 years. The three main worlds run on local high-speed NVMe SSD storage, while the archive worlds are mounted to the world path via Samba/CIFS from a slow HDD NAS on the local network since my players only visit these worlds during nostalgia events, there is no player activity on them at other times.

Due to the NAS's heavy workload (continuous backups, deduplication, compression, and checksumming) and the fact that it runs on HDDs, its I/O performance is poor. Although Paper's chunk system handles these slow read operations effectively, preventing them from affecting the game server itself, the operation to save level.dat still runs on the server thread. This causes the server to experience a spike in lag every so often (when you have a lots worlds, it will keep and continuously). Although these spikes las...

rustic folioBOT
rustic folioBOT
#

Expected behavior

I expect to see the speed not reset when the ender pearls are dropped.

Observed/Actual behavior

I see that when I flip the ender pearl, the speed is reset, although it shouldn't be.

Steps/models to reproduce

when a player goes forward or flies on elites and throws an ender pearl forward or throws an ender pearl into a vortex charge on elites, his speed slows down and he hovers in the air for a while or just stops on the ground, that is, slows down

Plugin and Datapack List

No

Paper version

26.1.2-65

Other

there is an example of the Pearl Momentum Fix plugin, but the problem is that because of it, players have a bug that sometimes they can just jump or take off on the spot, this should not happen, but the description of the plugin is correct and it needs to be done because the plugin does not cope with it.

rustic folioBOT
rustic folioBOT
#

Expected behavior

When opening a villager merchant menu for a player using the Paper API, I expected the villager's reputation-based trade behavior to work the same as when the player normally interacts with that villager.

For example, discounts or price changes caused by villager reputation should be applied to the trades shown in the merchant menu.

Observed/Actual behavior

When opening the merchant menu using MenuType.MERCHANT.builder(), the villager's reputation-based trade behavior does not appear to work.

The menu opens successfully, but the trades do not reflect the villager's reputation data for the player.

Code used:

MenuType.MERCHANT.builder()
    .merchant(villager)
    .checkReachable(false)
    .build(player)
    .open();

### Steps/models to reproduce


**Steps/models to reproduce**

```markdown
1. Start a Paper server with a plugin that opens a villager merchant menu using the Paper menu API.
2. Get or spawn a villager with trades.
3. Give the player a reputa...
rustic folioBOT
#

Well the logic for reputation is when you interact with the villager (before create the inventory to show), in the case of the MenuType you directly build the inventory then that step are ignored (like in HumanEntity#openMerchant)

Not sure for my if was intended or not... if its not intended then a fix can be call that method in HumanEntity#openMerchant and the CraftMenu#openMerchantMenu (used by the open() method in the MenyType API)

rustic folioBOT
#

Talking in discord about the Villager and the inventory this PR handle a behaviour noticed in https://github.com/PaperMC/Paper/issues/13905 where the methods to open inventory related to Villager ignore the update price for reputation or hero of the village, the only "breaking" change here is if user dont expect to get that change of prices, but just need use https://jd.papermc.io/paper/26.1.2/org/bukkit/inventory/MerchantRecipe.html#setIgnoreDiscounts(boolean) for make clear dont wanna updates in the prices.

Thanks @Y2Kwastaken and @masmc05 for the help with the Inventory behaviour.

Can close https://github.com/PaperMC/Paper/issues/13905

rustic folioBOT
rustic folioBOT
#

Currently the only way to get the entities loot on death is using EntityDeathEvent#getDrops, but that also includes drops from things like chest horses, boat chests, blocks held by enderman, etc.

If you only want to mutate that entities loot table you have to manually handle every edge case which is painful to say the least.

EntityLootGenerateEvent is intended to solve the gap.

rustic folioBOT
#

Stack trace

Plugin and Datapack List

Only have plugin!

pl
[10:28:58 INFO]: ℹ Server Plugins (43):
[10:28:58 INFO]: Paper Plugins (4):
[10:28:58 INFO]: - AdvancedServerList, MCKotlin-Paper, paper-language-kotlin, surf-serverbrand-customizer
[10:28:58 INFO]: Bukkit Plugins (39):
[10:28:58 INFO]: - ActionGlass, AnarchySpawn, AntiCheatAddition, AntiLoggedInFromAnotherLocation, AttackCooldownRemover, AttributeSwapFixer, BlockChat, BlockReports, Bunnysquad, BushRehab
[10:28:58 INFO]: LHTab, Milk, NewJoinMessages, NoChatLagServer, NoSleep, OtherBedRegen, OxygenGamemodeLock, packetevents, ProtocolLib, ReducedDebugInfo

Actions to reproduce (if known)

Can I add the repair update to papermc 1.21.11?
Moonrise is a big problem
Some cheating clients, such as PacketFly, can also experience the same crash

Paper version

ver
[10:29:28 INFO]: Checking version, please wait...
[10:29:28 INFO]: This server is running Paper version 1.21.11-132-ver/1.21.11@c5eb079 (2026-05-11T11:...

#

The symptoms are simple
A certain core of the CPU is running at 100% lag
[10:33:45 INFO]: UUID of player StoodMusic58914 is d1793670-3689-3b2a-8b70-c5ecabd45331
[10:33:50 WARN]: [ca.spottedleaf.moonrise.patches.chunk_system.level.entity.EntityLookup] Entity uuid already exists: 64b08d5b-9cec-4a20-8cf9-53dfb04c815e, mapped to Skeleton['Skeleton'/9295, uuid='64b08d5b-9cec-4a20-8cf9-53dfb04c815e', l='ServerLevel[world]', x=-196.50, y=79.92, z=301.35, cpos=[-13, 18], tl=0, v=false], can't add Skeleton['Skeleton'/29296, uuid='64b08d5b-9cec-4a20-8cf9-53dfb04c815e', l='ServerLevel[world]', x=-196.50, y=79.92, z=301.35, cpos=[-13, 18], tl=0, v=false]
Moonrise crashes again after entering the same chunk

#

kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:05 INFO]: UUID of player SM_Games is 6adde1b9-ac7d-37a4-8c21-a58b5dd98e0b
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:07 INFO]: Killed 31 entities
kill @e
kill @e
kill @e
[10:44:07 INFO]: Killed 718 entities
[10:44:07 INFO]: Killed 573 entities
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e

kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:10 INFO]: Killed 28432 entities
kill @ekill @e
[10:44:10 INFO]: Killed 28449 entities
kill @e
[10:44:10 INFO]: Expected whitespace to end one argument, but found trailing data
kill @ekill @e<--[HERE]
kill @e
kill @e
kill @e
kill @e
[10:44:11 INFO]: Killed 14545 entities
kill @e
[10:44:11 INFO]: Killed 10364 entities
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:13 INFO]: [+] SM_Games joined the server.
Welcome to SM.SMP
kill @e...

#

kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:05 INFO]: UUID of player SM_Games is 6adde1b9-ac7d-37a4-8c21-a58b5dd98e0b
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:07 INFO]: Killed 31 entities
kill @e
kill @e
kill @e
[10:44:07 INFO]: Killed 718 entities
[10:44:07 INFO]: Killed 573 entities
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
kill @e
[10:44:10 INFO]: Killed 28432 entities
kill @Ekill @e
[10:44:10 INFO]: Killed 28449 entities
kill @e
[10:44:10 INFO]: Expected whitespace to end one argument, but found trailing data
kill @Ekill @e<--[HERE]
kill @e
kill @e
kill @e
kill @e
[10:44:11 INFO]: Killed 14545 entities
kill @e
[10:44:11 INFO]: Killed 10364 entities
kill @e
kill @e
kill @e
kill...

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

How is it valid usage because of the namespace being lowercase? The key in the other constructor is made lowercase automatically, so I thought this would be acceptable.

It is made lowercase automatically when supplying an input because you do not control the input directly. Most plugins have a uppercase letter in their name somewhere which is a valid thing, and it would be a breaking change if every author would have to change this in order to use NamespacedKey. When specifying the namespace manually, you are in control, so this is no longer an issue and the correct requirements are enforced

#

because you do not control the input directly
You do though? I was talking about the key, not the namespace. You directly control the key, but it is still made lowercase. Should this change be removed?

When specifying the namespace manually, you are in control

I haven't been talking about the namespace, I've been talking about the key.

In both scenarios, you have full control over the key, but it is still changed to be made lowercase when the plugin class is specified. I also made the namespace string be lowercase because I though it'd be weird to throw errors for a capitalized namespace but not for a capitaized key.

rustic folioBOT
#

I mean, we cannot really remove it now as it already exists in the plugin constructor of NS without breaking backwards compatibility. that bit of the namespaced key constructor was inherited from spigot,

I agree with the above comments tho. Manually and quietly changing the key to lowercase seems only harmful when developers should very much be forced to use correct casing for these inputs.

rustic folioBOT
#

There's currently no event that fires when a creeper's swell level changes, and there's currently no way to stop a creeper from swelling. CreeperIgniteEvent does not fire when a creeper primes due to proximity, EntityExplodeEvent only fires at the end of swelling, and GenericGameEvent of type GameEvent.PRIME_FUSE doesn't allow for cancelling and doesn't fire for individual swell steps.

The proposed CreeperSwellEvent fires whenever a creeper's internal swell level changes, and it also differentiates different reasons for the swell: PRIMED (proximity or ignition), FALL_DAMAGE (falling from a height), or CUSTOM (plugin adjusting swell).

Fixes #12620

#

There's currently no event that fires when a creeper's swell level changes, and there's currently no way to stop a creeper from swelling. CreeperIgniteEvent does not fire when a creeper primes due to proximity, EntityExplodeEvent only fires at the end of swelling, and GenericGameEvent of type GameEvent.PRIME_FUSE doesn't allow for cancelling and doesn't fire for individual swell steps.

The proposed CreeperSwellEvent fires whenever a creeper's internal swell level changes, and it also differentiates different reasons for the swell: PRIMED (proximity or ignition), FALL_DAMAGE (falling from a height), or CUSTOM (plugin adjusting swell).

Fixes #12620

#
  1. Why wouldn't the client reflect the unswelling if cancelled, as it does if you back off from a creeper?

  2. I see you're firing a swell event on cancelled explosion. Bizarre edge case question: What happens if someone is always cancelling explosion events and then cancels that specific post-cancel swell event as well? Will the creeper be continuously trying to explode?

rustic folioBOT
#

After reading your reply, I noticed a bug that would let a primed creeper's swell level to continue to change even if the event was cancelled. It happened because cancelling the event set the final swell change to 0, so the vanilla logic kicked in and continued to increment the swell level. Now, the tick function will instead check for a nonzero swellDir to decide whether or not to fire the event and handle its cancellation state.


  1. Why wouldn't the client reflect the unswelling if cancelled, as it does if you back off from a creeper?

The client does render an unswell, but it seems like the client is only programmed to render a full swell in one direction. For example, if I use this code in a plugin to only allow a creeper to swell half-way:

@EventHandler
public void onCreeperSwell(CreeperSwellEvent event) {
    if (event.getCurrentSwell() + event.getFinalSwellChange() > event.getMaxSwell()/2)
        event.setCancelled(true);
}

the client still sees the...

rustic folioBOT
#

Expected behavior

ItemStack.getItemMeta() should work safely when called from multiple virtual threads concurrently.

Observed/Actual behavior

CraftMetaItem.updateFromPatch() throws NullPointerException at line 547 because ImmutableCollections$SetN.contains() receives a null argument. This happens when multiple virtual threads call getItemMeta() concurrently (via a plugin's async processor).
The UI still renders after a retry, so it's non-fatal but produces log spam.

Steps/models to reproduce

  1. Have a plugin that creates/accesses ItemStacks on virtual threads (or any async thread pool)
  2. Multiple threads call ItemStack.getItemMeta() concurrently
  3. NPE in updateFromPatch

Plugin and Datapack List

ℹ Server Plugins (43):
Paper Plugins (1):

  • FancyHolograms
    Bukkit Plugins (42):
  • 3DManeuverGear, AdvancedReplay, AlonsoLevels, AneCustomToast, AntiPopup, BrickThrower, Economy, ExtraSpecialItems, FakeBedWars, FakeExItems
    FakeRush, FakeServer, Gen-Splitter, Item...
rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] New branch created: dev/26.2
#

Were paper-server/patches/sources/org/apache/logging/log4j/core/appender/AsyncAppender.java.patch or paper-server/patches/sources/org/apache/logging/log4j/core/appender/AsyncAppenderEventDispatcher.java.patch intended?

#
[PaperMC/Paper] branch deleted: dev/26.2
rustic folioBOT
rustic folioBOT
#

I could maybe see a use case for being able to set one part of the rotation relative and the other absolute, which wouldn't be possible with just an addRotation(yaw, pitch) method. I'm not immediately a fan of the current proposed method since I dislike having ambiguous boolean parameters in methods, something like a setRotation(Something.relative(2f), Something.absolute(90f)) could fix that.

#
U5B

From: https://github.com/PaperMC/Paper/issues/12986#issuecomment-3217402824
Hi, any updates? I've come up with another fix: let projectiles force-load the chunk they're in. Once that chunk can tick, the despawn-time has enough time to remove the projectile. For safety, we could cap how many chunks a single projectile can load. Does that sound feasible to you?

I have come up with a different solution plugin-wise. Since World.getEntities and World.getEntitiesByClass return all accessible entities, we can loop through all entities and exclude the ones that are ticking.

This code will remove all entities in non-ticking chunks, which is not good, but this could be a starting point if you are still having this issue
(I also have not benchmarked it at all)

for (final var bWorld : Bukkit.getWorlds()) {
	if (bWorld.getPlayers().isEmpty()) {
		continue;
	}
	final var list = bWorld.getEntities();
	final var chunksToLoad = new LongArraySet();
	for (final var entity : list) {
		if (entity```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

I kinda know, the likelyhood that this will be accepted is slim, but this PR adds per player Quick Actions & Pause Menu Additions by hijacking the default Quick Actions & Custom Options dialogs and adding it to the corresponding Tag.

I would have rather wanted to add 2 extra pre packaged dialogs, but I couldn't find out how to do that.

example usage:

    @EventHandler
    public void onPlayerDialog(PlayerDialogsReceiveEvent event) {
        getLogger().info("Setting Dialog");
        event.setPauseMenuAdditions(Dialog.create(builder -> builder.empty()
            .base(DialogBase.builder(Component.text(event.getConnection().getProfile().getName() + "'s Pause Menu")).build())
            .type(DialogType.notice())
        ));
        event.setQuickAction(Dialog.create(builder -> builder.empty()
            .base(DialogBase.builder(Component.text(event.getConnection().getProfile().getName() + "'s Quick Actions")).build())
            .type(DialogType.notice())```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

This variable totalEntityAge seems always being saved, but only loads if entity is LivingEntity.

I believe there was a reason not to load it when it was tickCount, but since we have separated that, I don't see a reason why we don't load it anytime.

despawnTime could behave better on some projectiles (like wither skull) after this.

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

If statement is now removed.

I think we could keep the old API behavior.
bukkitEntity.getTicksLived now returns totalEntityAge , we can make it returns tickCount for non-LivingEntity.

However, I think a better approach, is to add new API, so dev can get both tickCount and totalEntityAge.
One for total age; One for ticked times since it's loaded.

rustic folioBOT
#

Is your feature request related to a problem?

This event would make it possible to know whether a spear has caused an entity to be dismounted.

Describe the solution you'd like.

A new event that is fired when a spear stab attack happens so that plugin developers can know when vehicles will be dismounted as a result of the spear attack.

Describe alternatives you've considered.

Looking at the VehicleExitEvent and getting data from the Entity's last damage event to check if it was attacked using a spear (DamageType).

Other

No response

rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

I know chunks are updated on load. But I need to convert 1.14/1.17 worlds to .slime format with AdvancedSlimePaper on 26.1.2, and ASP reads from disk, discarding old chunks. Without forceUpgrade (not implemented in 26.1) and without saving the world, how do I get the updated chunks to disk? i make custom fork plugin from originale source code of Slime-World-Manager native 26.1.2 this is why i need this features if is possible

Describe the solution you'd like.

a input for start bat who convert and upgrade old block from 1.14 to 26.1.2

Describe alternatives you've considered.

--force-upgrade --erase-cache nogui

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

Yes.

Plugins may need to associate information collected during the handshake phase with the player that later reaches AsyncPlayerPreLoginEvent, PlayerLoginEvent, or PlayerJoinEvent.

Currently, the only common identifier available in the early stages of the connection process is the remote IP address. However, IP addresses are not a reliable way to correlate a specific connection, as multiple connections can originate from the same address.

As a result, it is difficult for plugins to reliably determine which handshake belongs to which login attempt.

Describe the solution you'd like.

Expose a stable connection identifier (for example, getConnectionId()) that is available throughout the entire connection lifecycle.

The identifier should remain the same from the initial handshake until the connection is either closed or the player fully joins the server.

Ideally, it would be accessible from events such as:

  • PlayerListPingEven...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Replaces https://github.com/PaperMC/Paper/pull/8525

Both wither skulls and carved pumpkins fired a BlockDispenseEvent twice if they didn't spawn a mob.
This is possibly a behavior change, but as usual, it's actually a bug fix so the behavior before was wrong.

In general if the dispense action fails completely no event occur (i.e the item is not dispensed nor consumed), the event is only triggered for the action that will succeed (that is partially true currently but should be better now).
Also moved fluid pickup game event after the event for taking liquid in bucket since the event is cancellable.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

Yes. Currently, server administrators can only configure entity tracking ranges globally via the Spigot/Paper configuration files. For plugin developers, this blanket approach is highly limiting. There is no existing API method to modify these visibility distances dynamically or target specific, individual entities.

Describe the solution you'd like.

I would love to see an API implementation that allows developers to override the standard tracking range categories on a case-by-case basis per entity. This would allow us to drastically extend the view distance of important custom entities (like boss mobs or markers) or reduce it for performance optimizations without impacting the rest of the server.

Describe alternatives you've considered.

Adjusting global settings is the only current workaround, but it forces a choice between overall server performance and specific gameplay features.

Other

A similar concept was previous...

rustic folioBOT
#
[PaperMC/Paper] New branch created: dev/26.2
rustic folioBOT
rustic folioBOT
#

Since they are "archive" worlds, you can set chunks.auto-save-interval to -1 in paper-world.yml to disable auto save.

Btw, player data saving is also always on server thread. It operates 3 files once for each player, that's heavier than level data auto save.

Its still need to save since players will play a while on archived worlds.

Furthermore, adjusting the auto-save interval doesn't seem to solve the problem; it just makes it happen less frequently.

rustic folioBOT
rustic folioBOT
#

Set chunks.auto-save-interval to -1 should disable level data saving and chunks auto save, if there's no other plugins trying to save or unload the worlds. Chunks will still save on unload. Level data saves on shutdown. Both can be saved by /save-all or World.save().

There are cases that some chunk data have to syncLoad on server thread, mostly poi searching, can be triggered by for example using eye of ender / entity AI. It may be alleviated by increasing region file cache.

About the async issue.. Mojang does have a async saving logic for other level data (maps, raids, etc.), however for level.dat it's on server thread though it does not require much changes for async. There's no reason, maybe Mojang thinks it's a crucial file. However, Their file operations is not atomicly, so it's possible to leave no level.dat file if the process get terminated.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Reapply Patch #1279

Spigot 1.13 checks if any field (which are manually copied from the ItemStack's "tag" NBT tag) on the ItemMeta class of an ItemStack is set.

We could just check if the "tag" NBT tag is empty, albeit that would break some plugins. The only general tag added on 1.13 is "Damage", and we can just check if the "tag" NBT tag contains any other tag that's not "Damage" (https://minecraft.gamepedia.com/Player.dat_format#Item_structure) making the hasItemStack method behave as before.

Returns true if getDamage() != 0 or has damage tag or other tag is set.

In Paper 1.20.4 there was still this patch: https://github.com/PaperMC/Paper-archive/blob/ver/1.20.4/patches/server/0221-Don-t-call-getItemMeta-on-hasItemMeta.patch, probably just did not survive the component rewrite

rustic folioBOT
rustic folioBOT
#

Netty does not guarantee that a write future listener will run before later packets are queued for write. This can cause packets send after the compression packet to not be compressed even though the client expects them to be compressed. When using nio/epoll the write future is often completed right after the write is ran so this race condition doesn't really happen, however I do suspect there might be cases where it can rarely happen (like kernel buffers being full)

However if you implement io uring support you'll notice that this race condition constantly happens. This is is due to the future being resolved way "later" due to the split in submission / completion queue in io uring. This explains why previous attempts to adding io uring support in Paper had issues with compression https://github.com/PaperMC/Paper/pull/9141

This pr fixes it by actually setting up the compression right after writing the compression packet.

tdlr: fixes login compression errors that are rare with...

rustic folioBOT
#

Is your feature request related to a problem?

I wanna get the SpawnCategory for the EntityType and dont wanna summon an entity for get the SpawnCategory

Describe the solution you'd like.

A EntityType#getSpawnCategory

Describe alternatives you've considered.

Use paperweight.userdev for allow me to use the Craft class to convert to NMS EntityType get the Category and convert to Bukkit like this.

public static SpawnCategory getSpawnCategory(final EntityType entityType) {
    return org.bukkit.craftbukkit.util.CraftSpawnCategory.toBukkit(CraftEntityType.bukkitToMinecraft(entityType).getCategory());
}

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

I also was investigating on this issue and made a similar fix to yours, although I handled it with the PacketSenderListener:

+            this.connection
+                .send(
+                    new ClientboundLoginCompressionPacket(this.server.getCompressionThreshold()),
+                    PacketSendListener.thenRun(() -> {
+                        this.connection.setupCompression(this.server.getCompressionThreshold(), true);
+                        this.connection.send(new ClientboundLoginFinishedPacket(gameProfile));
+                    })
+                );

Something I wanted to note, is that Mojang seems to have created a Netty adapter that does literally nothing at Connection#configurePacketHandler L681.
I have the ~unconfirmed~ suspicion that this handler, considering its name, was made by Mojang to probably delay the packet sending enough to let the compression/decompression handlers be registered, which apparently io_uring is outspeeding. A more...

rustic folioBOT
rustic folioBOT
#

To complement the work done by Beanes in https://github.com/PaperMC/Paper/pull/13929, this PR implements io_uring transport to Paper, including its version of Unix Domain socket support.
As such, this PR depends on https://github.com/PaperMC/Paper/pull/13929 being merged first, as currently Minecraft seems to rely on a hacky workaround to hide a race condition while setting up compression.

I do agree that Paper might not get a huge boost from io_uring, since it won't handle as many active connections as Velocity, but Folia will most definitely get a significant improvement from this. And with this not being a region-related feature, it is more suitable have it on Paper and let Folia get it downstream.

This also relies on removing the synchronization in Connection#disconnect from the netty threads, as it will trigger Netty's deadlock prevention in the form of io.netty.util.concurrent.BlockingOperationException.
This used to be part of Paper, but was removed in https://github.com...

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Given this already break since 1.20.6, i'm not sure the damage exclusion is really needed now (which will break things again).

We could replace this damage check with iterating over DataComponentPatch#entrySet() and comparing against the ItemStack's prototype. But I feel like just checking the damage value is enough — what do you think?

for (final Map.Entry<DataComponentType<?>, Optional<?>> entry : this.handle.getComponentsPatch().entrySet()) {
    if (!Objects.equals(this.handle.getPrototype().get(entry.getKey()), entry.getValue().orElse(null))) {
        return true;
    }
}
return false;
rustic folioBOT
#

Expected behavior

The KeyedBossBar created via Bukkit#createBossBar(NamespacedKey) to be the same instance via Bukkit#getBossBar(NamespacedKey)

Observed/Actual behavior

In CraftServer#createBossBar(NamespacedKey), a new CustomBossEvent is created as well as a new CraftKeyedBossBar. However, the CraftKeyedBossBar is not stored on the newly created CustomBossEvent

So when using CraftServer#getBossBar(NamespacedKey) it grabs the CustomBossEvent, then calls #getBukkitEntity provided in a patch.
This patch method checks to see if a boss bar exists on the CustomBossEvent, if it does returns it, if it does not creates a new one then sets the boss bar field to this new instance.

Steps/models to reproduce

NamespacedKey key = new NamespacedKey("test");
KeyedBossBar bar1 = Bukkit.createBossBar(key);
KeyedBossBar bar2 = Bukkit.getBossBar(key);
if (bar1 == bar2) {
    // Wont ever be the case
} else {
   // Will always be the case
}

Plugin and Datapack List

[00:59:26```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Stack trace

Description: Exception in server tick loop
java.lang.RuntimeException: Failed to encode Minecraft Component: empty[style={color=gray,clickEvent=SuggestCommand[command=/hsay test]}, siblings=[literal{hsay test}[style={color=red,underlined}], translation{key='command.context.here', args=[]}[style={color=red,italic}]]]; Disallowed chat character: ''
	at io.papermc.paper.adventure.WrapperAwareSerializer.lambda$deserialize$0(WrapperAwareSerializer.java:28)
	at com.mojang.serialization.DataResult$Error.getOrThrow(DataResult.java:287)
	at io.papermc.paper.adventure.WrapperAwareSerializer.deserialize(WrapperAwareSerializer.java:28)
	at io.papermc.paper.adventure.WrapperAwareSerializer.deserialize(WrapperAwareSerializer.java:13)
	at io.papermc.paper.adventure.PaperAdventure.asAdventure(PaperAdventure.java:185)
	at net.minecraft.commands.Commands.finishParsing(Commands.java:445)
	at net.minecraft.commands.Commands.performCommand(Commands.java:373)
	at net.minecraft.commands.```...
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

If a world that players are in gets unloaded/reset, they end up spawning in the overworld at the same coordinates they were at.

This can cause players die suffocate in walls or fall to their death

There is no easy way to detect if a player spawn location has had its world changed, this patch fixes that by tracking if the world was determined to be invalid.

I added a constructor overload in-case some plugin author is manually creating AsyncPlayerSpawnLocationEvent instances for some reason.
I also removed boolean[] invalidPlayerWorld = {false}; local variable as it wasn't used for anything, let me know if you want it back.

Also apologies that this isn't in per-file patch format, I could not get it working correctly.

rustic folioBOT
rustic folioBOT
#

Expected behavior

You should not receive the error message Height limit for building is 319 when standing on a shulker box with high latency and opening and closing it a few times.

Observed/Actual behavior

When you have high latency towards the server, stand on a shulker box and open and close it a few times pretty quickly, you'll see the action bar Height limit for building is 319 appear in red.

Steps/models to reproduce

  • Produce a situation in which you have high latency towards the server. A Linux command like sudo tc qdisc add dev <interface> root netem delay 1000ms should be able to achieve that if you're not local-hosting.
  • Stand on a shulker box
  • Open and close said shulker box a few times while standing still on it

Plugin and Datapack List

No plugins or datapacks were installed during my testing

Paper version

26.1.2-69

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

[10:10:55 ERROR]: [PluginRemapper] Encountered exception remapping plugins
java.util.concurrent.CompletionException: java.lang.RuntimeException: Failed to remap plugin jar 'plugins[C]CosmeticsCore_1.3.11.jar'
at java.base/java.util.concurrent.CompletableFuture.wrapInCompletionException(CompletableFuture.java:323) ~[?:?]
at java.base/java.util.concurrent.CompletableFuture.encodeThrowable(CompletableFuture.java:359) ~[?:?]
at java.base/java.util.concurrent.CompletableFuture.completeThrowable(CompletableFuture.java:364) ~[?:?]
at java.base/java.util.concurrent.CompletableFuture$UniApply.tryFire(CompletableFuture.java:670) ~[?:?]
at java.base/java.util.concurrent.CompletableFuture$Completion.run(CompletableFuture.java:503) ~[?:?]
at java.base/java.util.concurrent.ThreadPoolExecutor.runWorker(ThreadPoolExecutor.java:1090) ~[?:?]
at java.base/java.util.concurrent.ThreadPoolExecutor$Worker.run(ThreadPoolExecutor.java:614) ~[?:?]...

rustic folioBOT
#

Description

This PR adds a maximum size limit to the ServerboundDebugSubscriptionRequestPacket codec.

Debug subscription packets are known to be abused by hack clients, in local testing, one client was able to fully occupy at least one Netty IO thread on a high-end system without triggering Paper's packet limiter.

<img width="1400" height="750" alt="image" src="https://github.com/user-attachments/assets/a7982f38-03f6-49c9-994e-0b96d0f63d8c" />

Fix

Requests containing more than 64 subscriptions are now rejected and disconnect the client with a DecoderException to avoid excessive CPU usage and memory alloc.

The max size should be changed once Mojang adds more subscriptions in DebugSubscriptions.

#

I think we should set the value in the configuration settings and disable it by default

Could you clarify when this limit would need to be disabled or changed? The current vanilla debug subscription count is 16, so 64 seems safe above the expected value while still preventing abusive decode sizes.

I am not sure Paper's global configuration is guaranteed to be loaded before this codec is initialized.

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Adds a few methods for batch registering & unregistering recipes to save on a LOT of tick time (and bandwidth when players are online) when compared to doing tons of add/remove recipe calls.

Also adds a hasRecipe method to avoid converting a bukkit recipe when its unnecessary.

In order to do this I extracted the creation of the minecraft recipe classes from the existing CraftRecipe#addToRecipeManager method to a new CraftRecipe#toMinecraftRecipe method, for use by the new methods. I also extracted the conversion of the bukkit recipe classes to the craft recipe classes to CraftRecipe.

In terms of performance improvements I was implementing this solution manually for a plugin I work on here: https://github.com/pylonmc/rebar/pull/827 where you can see the differences

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

Even while a Paper server is under severe load, all world and player inventory saving operations should occur simultaneously, eliminating the possibility for duplication exploits by exploiting failed saving on either end.

Observed/Actual behavior

A severe lag machine created by another player on this Paper server at the time caused player data to stop saving while the world chunks remained active. This allowed items to be dropped, the player to disconnect, and the inventory, enderchest, all player data in general, to roll back upon rejoining, resulting in duplicated items.

Steps/models to reproduce

Put a Paper server under severe load (using a lag machine).
Rejoin the server quickly. If the lag is of the right type, the world chunks will remain active while player data fails to save, resulting in inventory and enderchest rollbacks.

Plugin and Datapack List

<img width="975" height="107" alt="Image" src="https://github.com/user-attachmen...

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

Info per lo sviluppatore:
Su Paper 26.1.2-66 l'evento io.papermc.paper.event.player.PlayerScoreboardChangedEvent non è disponibile, quindi il Glow usa il fallback task (ogni 40 tick). Il plugin funziona correttamente. Verificare se Paper ha introdotto l'evento in un build successivo al 66 per poter eliminare il warn.

Observed/Actual behavior

latest.log

Steps/models to reproduce

no comment

Plugin and Datapack List

no comment

Paper version

no comment

Other

No response

rustic folioBOT
rustic folioBOT
#

After investigating the issue further, it occurs when thread A modifies the itemmeta and thread B calls ItemStack#clone()#getItemMeta(). While this is certainly not supported behavior, it might be good for you to know.

My suggestion is to either include a synchronization mechanism of the underlying components/data patch, or to throw an concurrency exception to avoid such cryptic errors in the future. Unfortunately I don't have time to create a PR myself

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

Setting up a very fast redstone clock linked to a notebook yeilds a conistent beat from the noteblock, see video for reference

https://streamable.com/mu80b2

Observed/Actual behavior

Setting up a very fast redstone clock linked to a notebook yeilds an onconsistent beat with a tiny barely noticiable pause from the noteblock, see video for reference

https://streamable.com/qj0gnb

Steps/models to reproduce

I'm not entire sure what is causing this but you can run the same test as me to figure hopefully figure it out

Plugin and Datapack List

Paper Plugins: CustomDiscs, emotecraft, PunisherX, SkBee

Bukkit Plugins: AdminCommands, AFKPlus, AntiVillagerLag, AuthMe, AxiomPaper, BedrockBreaker, Chunky, ChunkyBorder, CommandAPI, CoreProtect, craftableinvframes, CustomAnvil, CustomJoinMessages, DebugStick, DiscordSRV, dynmap, EarthquakePlugin, EasyArmorStands, ElytraEssentials, EntityDetection, GSit, HarvestHelper, HeadDB, HelpCommand, HiddenAr...

#

That just seems like server lag/unstable TPS. If the server isn't running perfectly at 20 TPS, you will get this behaviour with contraptions like this. I am not able to reproduce this issue myself on a well-performing server.

Generally though: We can't really take third-party issue reports like this. It is up to the server admin to reproduce this without plugins, to provide logs, etc. If you have no access to the server, an issue report is of little use as you can't provide the required details or test things.
Especially with plugins like Skript that could do anything.
Please bring up the issue to the admin of the server instead.

rustic folioBOT
#

for anyone wondering or having a similar issue: none of the plugins/datapacks mentioned in the post caused lag or redstone beat skip. There was an audible lag due to high ping. Rhett has a very specific storage system that might relay on ignore-occluding-blocks setting. While setting it to false provides more vanilla-like experince, disabling it might cause perfomance issues.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

According to minecraft source code (Verified Version : 26.1.2), this condition is not a hard requirement.
Minecraft checks if the given block is a Bed (like done here) BUT it doesn't need it, it checks it to ensure the new data for the block (marked as occupied)

This is becoming a inactive PR but I believe this is a great adding so, if no one is taking it, I might re-do it but I believe the guy who have done this PR just doesn't have notifications

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Problem

Some plugins, Slimefun, or its addons, for example, provide even higher enchantment levels compared with the vanilla enchantments. And players can craft the crossbow with a higher enchat level. Thus, it can create a long projectile item list in CrossbowItem#draw (EnchantmentHelper#processProjectileCount).
Unlike the projectile size limit in CODEC, the exception throwing under these constructors will not be caught; it crashes the server instead.

example error:
<img width="2515" height="962" alt="ba1f61b2eaa97c1669851643c2b6aa9f" src="https://github.com/user-attachments/assets/71cc1d5a-b5bc-4089-8153-5961bcf13e01" />

Fix

So it's better to use a soft limit here to prevent the server crash caused by the hard throw.
Not sure whether we still need to keep the warning message.

rustic folioBOT
rustic folioBOT
#

not sure about this change... for example the ChargedProjectiles throw was added by Paper but in 26.2 now its a thing added by Mojang (with a more high limit)

Yeah, did a quick check, you are right. However, in 26.2, Mojang used stream limit + warning to handle the item list with the size bigger than 1024, so it will not throw if the call is from CrossbowItem#tryLoadProjectiles (Like in the above error).

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

canBeReplaced(Fluid) is just equivalent to state.canBeReplaced() || !state.isSolid() with two exceptions for end blocks. So i'm not sure this is really needed, the fluid parameter is not even used currently.

I would argue for intuitiveness this is still a good addition, no developer that doesn't check or already know the NMS logic is going to intuitively know/guess that a block can be replaced by fluids if either block.isReplaceable() or !block.isSolid(), and if Minecraft ever does add blocks with more complex behavior (such as using the fluid parameter) then it would be automatically handled.

rustic folioBOT
rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] New tag created: 26.1.2
#
[PaperMC/Paper] New branch created: ver/26.1.2
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

The speed effect should be removed once the player is no longer wearing boots with Soul Speed.

Observed/Actual behavior

The speed effect remains active for the entire session regardless of surface, does not reset on death, but is removed upon reconnecting to the server.

Steps/models to reproduce

  1. Have two pairs of boots enchanted with Soul Speed - one nearly broken and one with full durability
  2. Equip the nearly broken boots and start running on soul sand while rapidly swapping between the two pairs
  3. Once the boots break, the speed effect persists for the entire session and applies on any surface

Plugin and Datapack List

ℹ Server Plugins (0):

Paper version

This server is running Paper version 26.1.2-70-ver/26.1.2@70eaed6 (2026-06-14T10:18:21Z) (Implementing API version 26.1.2.build.70-stable)
You are running the latest version

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

Translatable components being resolved server-side.

Observed/Actual behavior

Translatables are not processed in any way.

Steps/models to reproduce

Dialog dialog = Dialog.create(builder -> builder.empty()
    .base(DialogBase.builder(Component.translatable("mytranslation.colorful")).build())
    .type(DialogType.notice())
);
player.showDialog(dialog);

Plugin and Datapack List

  • test

Paper version

This server is running Paper version 26.1.2-70-ver/26.1.2@70eaed6 (2026-06-14T10:18:21Z) (Implementing API version 26.1.2.build.70-stable)
You are running the latest version

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Expected behavior

Items should not be removed

Observed/Actual behavior

Items are removed

Steps/models to reproduce

In the PlayerInteractEvent listener, you need to update the item in the player's hand, and in the BlockPlaceEvent listener, you need to cancel the event. Since the block isn't being placed, the item shouldn't be removed, but it is being removed.

Plugin and Datapack List

none

Paper version

latest 26.1.2

Other

https://youtu.be/yBz6xdmOukU

rustic folioBOT
#
public final class TestPlugin extends JavaPlugin implements Listener {

    @Override
    public void onEnable() {
        this.getServer().getPluginManager().registerEvents(this, this);
    }

    @EventHandler
    public void interact(PlayerInteractEvent event) {
        Player player = event.getPlayer();
        PlayerInventory inventory = player.getInventory();
        ItemStack itemInMainHand = inventory.getItemInMainHand();
        player.getInventory().setItemInMainHand(itemInMainHand);
    }

    @EventHandler
    public void place(BlockPlaceEvent event) {
        event.setCancelled(true);
    }
}
#

Yea, as said, modifying the item in the players hand is generally going to desync the servers logic, it's not viable or tenable to track what weird interactions people are doing with inventories inside of those events; This is a quirky area but really works as expected

#
[PaperMC/Paper] New branch created: feature/adventure-5-copy
rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] branch deleted: feature/adventure-5-copy
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Yes, the possibilities conceived by the community but not incorporated by the manufacturers. And here’s yet another case of “It’s not a bug, it’s a feature (request).” Since I’m currently struggling with the challenges of extending the range of values below -64 (also a datapack with Y = -256), I came across a fix for Fabric by warior456. Helpfully, this fix includes a value defined via a configuration file, adjustable to BELOW_SEA_LEVEL, ABOVE_BOTTOM, and ABSOLUTE. I’d love to see similar flexibility for Paper.

In my datapack, I set the sea level to 0 right away and ran into a pretty ugly glitch in the way the horizon is displayed. But that's another story...

rustic folioBOT
#

Expected behavior

Thrown ender pearls should behave identically to vanilla (they should not respawn after being deleted and the thrower relogging), and there should be no warnings about duplicate versions of them in the console.

Observed/Actual behavior

If a player has a stasis chamber set up with one or more pearls and the server restarts, whenever that player joins the server, the following warning appears in the console - one for each pearl:

[15:37:48 WARN]: [ca.spottedleaf.moonrise.patches.chunk_system.level.entity.EntityLookup] Entity uuid already exists: 33bcecaa-0f27-467e-bab0-9f966e633f5b, mapped to ThrownEnderpearl['Thrown Ender Pearl'/153, uuid='33bcecaa-0f27-467e-bab0-9f966e633f5b', l='ServerLevel[world]', x=-14.43, y=111.18, z=-15.71, cpos=[-1, -1], tl=0, v=true], can't add ThrownEnderpearl['Thrown Ender Pearl'/155, uuid='33bcecaa-0f27-467e-bab0-9f966e633f5b', l='```...
rustic folioBOT
#
[PaperMC/Paper] New branch created: feature/dc
rustic folioBOT
#

Expected behavior

No exceptions, commands should work

Observed/Actual behavior

NoClassDefFoundError

Steps/models to reproduce

run any spark command like: /spark

Plugin and Datapack List

[20:55:57 INFO]: ℹ Server Plugins (1):
[20:55:57 INFO]: Paper Plugins:
[20:55:57 INFO]: - Worlds

[20:56:01 INFO]: There are 3 data pack(s) enabled: [vanilla (built-in)], [paper (built-in)], [file/bukkit (world)]
[20:56:01 INFO]: There are no more data packs available

Paper version

[20:56:15 INFO]: This server is running Paper version 26.2-22-dev/26.2@1142778 (2026-06-18T11:51:25Z) (Implementing API version 26.2.build.22-alpha)
You are running the latest version
Previous version: 26.1.2-65-fd45f4b (MC: 26.1.2)

Other

[spark] Exception occurred whilst executing a spark command
java.lang.NoSuchMethodError: 'net.kyori.adventure.text.BuildableComponent net.kyori.adventure.text.TextComponent$Builder.build()'
        at me.lucko.spark.paper.common.comman```...
rustic folioBOT
rustic folioBOT
#

Expected behavior

Nether file should have been generated in the dimensions directory

<img width="746" height="214" alt="Image" src="https://github.com/user-attachments/assets/bd97350b-bce6-43ab-8e8d-b1e9a2b0c52b" />

Observed/Actual behavior

Only created Overworld and The End files. It also skips The Nether during server startup. Either loading an existing world, or a brand new world.

Vanilla creates the world no problem.

Steps/models to reproduce

Create a brand new world in Paper Minecraft version 26.1.x

Plugin and Datapack List

BlueMap
DiscordSRV

Paper version

This server is running Paper version 26.2-23-dev/26.2@250ea42 (2026-06-18T19:00:47Z) (Implementing API version 26.2.build.23-alpha)
You are running the latest version
Previous version: 26.1.2-71-2dc3641 (MC: 26.1.2)

(26.1.2 also has the same issue.)

Other

No response

rustic folioBOT
#

I completely understand your point. It’s just this: Doesn’t the ability to change parameters like min_y, sea_level, height, etc., in the datapacks practically necessitate - or even require - changes to core mechanisms like chunk generation? It simply doesn’t make any sense to be able to set the depth to as low as -2032 blocks if the only result is a lava pool that might be 1978 blocks deep.

But ultimately, this is a “bug” that Mojang hasn't really addressed since version 1.18.

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Doesn’t the ability to change parameters like min_y, sea_level, height, etc., in the datapacks practically necessitate - or even require - changes to core mechanisms like chunk generation?

Yes, but the nature here is that when mojang added this stuff they used the existing defaults, you didn't login to the server one day and your sea/lava levels suddenly transformed and all of a sudden you had a world with the ocean at two different levels.

I'm not against something being added here, but it needs to be deactivated by default so that it doesn't change the output for peoples worlds during a random patch release, nor do we really want to be involved in adding custom options directly into datapacks themselves

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

This doesn't seems to work?
Got the following " [net.minecraft.server.network.config.PrepareSpawnTask] Serialization errors:
ServerPlayer['Lulu13022002'/100, uuid='74442095-f151-4e35-aeb9-b5142a9926ab', l='ServerLevel[world]', x=-10.54, y=77.00, z=6.93, cpos=[-1, 0], tl=0, v=true](Lulu13022002 at -10.540502490895227,77.0,6.933107692844611): Failed to decode value '{Slot:0b,components:{"minecraft:attribute_modifiers":[{amount:5.0d,id:"minecraft:kenny",operation:"add_multiplied_base",type:"minecraft:nameplate_distance"}]},count:1,id:"minecraft:stone"}".

It looks like this class doesn't do the distinction between the old and the new format of component like AttributesRenameFix.

rustic folioBOT
#

Closes #13941

As far as I can tell this line being there doesn't make a lot of sense and is likely a leftover, see https://github.com/PaperMC/Paper/issues/13941#issuecomment-4642200340 for mcsrc links for comparing.

Before, this line was an else for a statement that checked the height, but after the changes in that snapshot it's now an else for the this.awaitingPositionFromClient == null && level.mayInteract(this.player, pos) check, which is wrong since neither of those have anything to do with reaching max height.

rustic folioBOT
#

Expected behavior

As far as I can tell, this repository did not used to proxy Maven Central. Perhaps this changed recently in relation to PaperMC's switch to JFrog Artifactory Israeli software. I don't know.

If this is intended, I would expect it to be documented. The repository is recommended for all starting plugin developers, and taking over Maven dependency resolution for central artifacts is surely unexpected behavior.

If it is not intended, well, you could save a lot of bandwith and resource usage by not proxying Maven Central. Some of my project's builds are failing with corrupted central artifacts, maybe because your repository is not handling the load, though I am unsure.

Observed/Actual behavior

The maven-public repository path proxies Maven Central. For example, take the following jar. It is resolved by the PaperMC repository instance, despite being an artifact located on Maven Central.

https://repo.papermc.io/repository/maven-public/org/slf4j/slf4j-a...

rustic folioBOT
#

It's a good practice to cache stuff in own repositories so stuff like CI can be faster and more reliable, including paper's CI of building and publishing paper builds, api and dev bundle. This is also true for a majority of other repositories I've seen, that's why it's recommended https://docs.gradle.org/current/userguide/best_practices_dependencies.html#use_content_filtering

rustic folioBOT
rustic folioBOT
rustic folioBOT
#
[PaperMC/Paper] New branch created: fix/craftregistry-concurrent-cache
#

Problem

CraftRegistry lazily populates its backing cache on every get() call, so a plain HashMap was being both read and written without any synchronization.

Registries are not main-thread-only in practice — we fully expect plugins to resolve registry entries off the main thread. Building an ItemStack, looking up an Enchantment, or resolving a BlockType/ItemType from an async task all funnel through CraftRegistry#get, and since get() mutates the cache on first lookup, those "reads" race against each other.

Under concurrent access a HashMap can corrupt its internal table on a put()-triggered resize, leading to torn/null reads and — specific to this cache — duplicate wrapper instances for the same registry entry, which breaks identity assumptions both plugins and CraftBukkit make about registry constants.

Change

  • Switch cache to a ConcurrentHashMap.
  • Collapse the get()-then-put() sequence into a single atomic computeIfAbsen...
rustic folioBOT
#

Pull request overview

This PR hardens CraftRegistry#get for off-main-thread access by making its lazy cache population thread-safe, addressing unsafe concurrent reads/writes to a plain HashMap when plugins build ItemMeta asynchronously.

Changes:

  • Replace the backing cache with a ConcurrentHashMap.
  • Use computeIfAbsent to atomically load and cache registry entries.
  • Make lockReferenceHolders volatile to ensure cross-thread visibility from the get() path.

💡 <a href="/PaperMC/Paper/new/dev/26.2?filename=.github/instructions/*.instructions.md" class="Link--inTextBlock" target="_blank" rel="noopener noreferrer">Add Copilot custom instructions</a> for smarter, more guided reviews. <a href="https://docs.github.com/en/copilot/customizing-copilot/adding-repository-custom-instructions-for-github-copilot" class="Link--inTextBlock" target="_blank" rel="noopener noreferrer">Learn how to get started</a>.

#

I feel that this falls into that annoying area of "that ship has already sailed", if we wanted to restrict this it would

  1. need to be on a proper release
  2. Have a warning
  3. have a carve out

26.x makes this honestly much better of a situation now that the folder layout is more sane in Paper; it's worth noting that this was always understood to me as basically being the save folder, and so it's really not a concern that it can be saved out of tree, if anything that smells like a part baked feature

rustic folioBOT
rustic folioBOT
#

Expected behavior

Log "test" on enable

Observed/Actual behavior

Log "null" on enable

Steps/models to reproduce

public final class Test extends JavaPlugin {
    @Override
    public void onEnable() {
        final ItemStack item = ItemStack.of(Material.SULFUR_CUBE_BUCKET);
        final NamespacedKey key = new NamespacedKey(this, "test");
        item.editMeta(meta -> meta.getPersistentDataContainer().set(key, PersistentDataType.STRING, "test"));
        final String value = item.getItemMeta().getPersistentDataContainer().get(key, PersistentDataType.STRING);
        getLogger().info(value);
    }
}

Plugin and Datapack List

[06:57:26 INFO]: ? Server Plugins (1):
[06:57:26 INFO]: Paper Plugins:
[06:57:26 INFO]: - Test

[06:57:43 INFO]: There are 3 data pack(s) enabled: [vanilla (built-in)], [file/bukkit (world)], [paper (built-in)]
[06:57:43 INFO]: There are no more data packs available

Paper version

[06:57:51 INFO]: This server is run...

rustic folioBOT
#

A "workaround" for the PDC can be just directly use the method in the ItemStack and avoid use ItemMeta.
ex.

public final class Test extends JavaPlugin {
    @Override
    public void onEnable() {
        final ItemStack item = ItemStack.of(Material.SULFUR_CUBE_BUCKET);
        final NamespacedKey key = new NamespacedKey(this, "test");
        item.editPersistentDataContainer(persistentDataContainer -> persistentDataContainer.set(key, PersistentDataType.STRING, "test"));
        final String value = item.getPersistentDataContainer().get(key, PersistentDataType.STRING);
        getLogger().info(value);
    }
}
rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

There's two reasons:

  1. It's shorter than item.getType().asItemType() and block.getType().asBlockType().
  2. With the new ItemType and BlockType API, it seems only logical, that the "legacy" Material class will be deprecated and removed at some point. So adding these methods and having developers use them could add to these developers' plugins longevity.

Describe the solution you'd like.

A method getItemType() on ItemStack and a method getBlockType().
The implementation would either be getType().asItemType() and getType().asBlockType(), or better, ItemStack and Block could just carry an ItemType or BlockType instance.
The second option would make even more room for truly custom items.

Describe alternatives you've considered.

Unnecessary field for this issue

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Spark Profile

a

Description of issue

[20:47:29 ERROR]: Illegal ChunkMap::addEntity for world SkyPvP: ServerPlayer['nEmanuel730'/3510685, uuid='32ff97a2-b139-3a54-ba40-1b77c5b02a35', l='ServerLevel[SkyPvP]', x=-36.24, y=128.62, z=-99.14, cpos=[-3, -7], tl=0, v=false, removed=UNLOADED_WITH_PLAYER](nEmanuel730 at -36.24086246742672,128.61693492105303,-99.13728069429358)
java.lang.Throwable: null
at net.minecraft.server.level.ChunkMap.addEntity(ChunkMap.java:955) ~[paper-1.21.10.jar:1.21.10-85-d98142e]
at net.minecraft.server.players.PlayerList.placeNewPlayer(PlayerList.java:281) ~[paper-1.21.10.jar:1.21.10-85-d98142e]
at net.minecraft.server.network.config.PrepareSpawnTask$Ready.spawn(PrepareSpawnTask.java:313) ~[paper-1.21.10.jar:1.21.10-85-d98142e]
at net.minecraft.server.network.config.PrepareSpawnTask.spawnPlayer(PrepareSpawnTask.java:139) ~[paper-1.21.10.jar:1.21.10-85-d98142e]
at net.minecraft.server.network.ServerConfigurationPa...

rustic folioBOT
#

Expected behavior

When using the World#spawn method to spawn a slime (e.g. player.getWorld().spawn(player.getLocation(), Slime.class), it spawns the slime like it does with any other entity.

Observed/Actual behavior

When the aforementioned method is used to spawn a slime, it raises the following exception:

[20:20:57 INFO]: Thatsmusic99 issued server command: /spawnslime
[20:20:57 ERROR]: Command exception: /spawnslime
org.bukkit.command.CommandException: Unhandled exception executing command 'spawnslime' in plugin PlaygroundPlugin v1.0-SNAPSHOT
        at org.bukkit.command.PluginCommand.execute(PluginCommand.java:47) ~[paper-api-26.2.build.29-alpha.jar:?]
        at io.papermc.paper.command.brigadier.bukkit.BukkitCommandNode$BukkitBrigCommand.run(BukkitCommandNode.```...
#

Expected behavior

While player is tempting animal with food.
Cow cow = EntityMoveEvent.getEntity(); <-- animal
cow.getTarget() <--- returns Player object of player that's doing the tempting

Observed/Actual behavior

cow.getTarget(); is not a Player object

but EntityTargetLivingEntityEvent.getTarget() correctly returns a targeting player
I'm guessing this is due to my observation, which is that cow re-targets the player every two ticks or so.

Steps/models to reproduce

  1. Use MWE plugin: https://github.com/kacpermajkowski/AnimalTargetIssueMWE
  2. Use commands on the server:
  • /gamerule spawn_mobs false
  • /gamerule spawn_monsters false
  • (multiple times if needed, to be sure no other cows are present) /minecraft:kill @e
  1. Spawn a Cow
  2. Take wheat in your hand and make the Cow follow you
  3. What you see is that checking Mob.getTarget() in EntityMoveEvent returns a non-Player object, and at the same time EntityTargetLivingEntityEvent.getTarget() returns a Pla...
rustic folioBOT
#

Expected behavior

LivingEntity.getRemoveWhenFarAway() returns false for Cow, false nametagged Zombie, true for regular Zombie

Since the documentation states:

"Returns if the living entity despawns when away from players or not.
By default, animals are not removed while other mobs are.

Returns:
true if the living entity is removed when away from players"

then it follows that for any entity that keeps existing after all players are farther than 128 blocks the method returns false, otherwise true.

Observed/Actual behavior

LivingEntity.getRemoveWhenFarAway() returns 'true' for Cow, 'true' for regular Zombie

So the logical conclusion I pointed out in expected behaviour section is not met.

Steps/models to reproduce

use LivingEntity.getRemoveWhenFarAway() in any context e.g. EntityMoveEvent and test on Cow and Zombie.

Plugin and Datapack List

datapack list
[22:17:45 INFO]: There are 3 data pack(s) enabled: [vanilla (built-in)], [file/bukkit (world)], [...

#

I don't know honestly, maybe there is some mismatch between "tempting" and "target", but I'm currently using animal.getBrain().getMemory(MemoryModuleType.TEMPTING_PLAYER); for Brain-using Animals, and ```NMS.Mob.goalSelector.getAvailableGoals().stream()
.filter(w -> w.getGoal() instanceof TemptGoal && w.isRunning())
.map(w -> {
try {
return w.getGoal().player;
} catch (IllegalAccessException e) {
return null;
}
})
.filter(Objects::nonNull)
.findFirst()

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

Spark Profile

Not possible to spark this early on, visual vm screenshot below

Description of issue

For a world that is 500gb for example world migration just takes so long

<img width="1533" height="525" alt="Image" src="https://github.com/user-attachments/assets/f952e610-f124-4e6a-8418-71daafcf14ef" />

shouldn't it just be renaming a few folders? why does it have to parse and check attributes for millions of files

Plugin and Datapack List

N/A

Server config files

N/A

Paper version

26.1.2 76d2ac758cb3abe75aceefa88207443768f585c6

Other

No response

rustic folioBOT
#

The migration logic spins up a copy-on-write FS in a temporary directory to prevent your world from possibly being left corrupted if the server dies during the migration.

Spinning up that COW FS on large large folders sadly is not very fast but I don't think paper should remove such precautions and possibly leave worlds in a broken state if the server process fails during the process.

rustic folioBOT
rustic folioBOT
rustic folioBOT
#

I have encountered this bug when upgrading my server as well, this also affects other plugins than Spark on my end.

This is my version: This server is running Paper version 26.2-30-dev/26.2@43f4dcd (2026-06-21T19:43:11Z) (Implementing API version 26.2.build.30-alpha)
You are running the latest version
Previous version: 26.1.2-64-2186e1e (MC: 26.1.2)

rustic folioBOT
rustic folioBOT
#

Is your feature request related to a problem?

A plugin I work on for a server has entity claims. Previously, just listening for entity damage and entity interact events was fine, but with sulfur cubes neither of those seem to be called when you punch them while they have a block.

Describe the solution you'd like.

Adding a cancellable event to sulfur cube punching.

Describe alternatives you've considered.

Raycasting during the arm swing animation to reset velocity. This has some issues such as stopping a cube entirely if it's already moving, along with being bypassable since some members use freecam.

Other

No response

rustic folioBOT
rustic folioBOT
rustic folioBOT
#
3z

Expected behavior

The connection throttle cleanup (every 200 connections) should remove only entries older than connectionThrottle milliseconds from the tracker map.

Observed/Actual behavior

The cleanup at ServerHandshakePacketListenerImpl, line 97 in the applied source, removes every entry because the predicate compares a raw System.currentTimeMillis() timestamp against the connectionThrottle config value (typically a few thousand ms):

throttleTracker.values().removeIf(time -> time > connectionThrottle);

time is a stored System.currentTimeMillis() value (~1.7×10¹²), and connectionThrottle is something like 4000. The condition 1700000000000 > 4000 is always true, so the entire map is wiped on every cleanup cycle.

Should be:

throttleTracker.values().removeIf(time -> currentTime - time > connectionThrottle);

(The currentTime local is already in scope — it's declared a few lines above at line 79.)

Steps/models to repr...

rustic folioBOT
rustic folioBOT
#

Expected behavior

When crouch placing an armour stand on top of a Redstone ore block, the block should activate/deactivate allowing for a random timer that can be observed.

Observed/Actual behavior

Doing the same in 26.1.2 no longer works. The Redstone ore block remains unlit. I have tested on Paper, Purpur, Fabric and Vanilla. It works in both Vanilla and on a Fabric server, but not on Paper or Purpur

Steps/models to reproduce

Place a Redstone ore block - Crouch place an armor stand on top - the ore block should light up. When it deactivates it should activate again since an entity is on top of it

Plugin and Datapack List

Tested with no plugins or data packs to confirm the issue still exists. Also removed and refreshed all config files to rule out changes that may have been made

Paper version

[22:36:49] This server is running Paper version
26.1.2-72-ver/26.1.2@1a6b910 (2026-06-19T13:08:47Z)
(Implementing API version 26.1.2.build.72-stable)
You a...

rustic folioBOT
#

Expected behavior

When a plugin updates sign text using either the Component-based SignSide#line(int, Component) API or the String-based SignSide#setLine(int, String) API, and then calls sign.update(true, true), online players should visually see the updated sign text without needing to disconnect and reconnect.

Observed/Actual behavior

The sign state updates server-side. Reading the lines back immediately after sign.update(true, true) shows the new text.

However, online players do not visually see the updated sign text. I tested this with two different connected clients, and both clients continued seeing the old sign text after running the test command.

If a player disconnects and reconnects, the updated sign text becomes visible. This happens with both Component-based updates and String-based updates.

Steps/models to reproduce

  1. Start a Paper server.
  2. Install a small test plugin with the command below.
  3. Place a sign and look directly at it....
rustic folioBOT