Working UltimateShopPriceProvider + Testing

Removing import, adding reflect

Took 1 hour 28 minutes
This commit is contained in:
Molzonas 2025-08-26 14:58:59 +02:00
parent 1f4176eec4
commit a6f7bf3dac
6 changed files with 97 additions and 38 deletions

View File

@ -1,25 +1,16 @@
# Painful Lost
# Painful Loss
Le plugin Minecraft fait pour montrer le regret de l'équipement perdu.
* Indique dans le chat le prix de l'équipement complet perdu à la mort
* Affiche l'élément le plus cher perdu
* Utilise les prix du fichier worth.yml de Essentials (fallback) ou les prix de UltimateShop (recommandé)
**Requiert d'avoir UltimateShop >= 3.10.2 !**
Suite du README à venir.
## Développement - Mise en place
* Clonez Painful Loss
* Téléchargez la dernière version de UltimateShop
* Ajoutez UltimateShop à votre repository local : `mvn install:install-file -Dfile="[chemin]/UltimateShop.jar" -DgroupId="cn.superiormc" -DartifactId="ultimateshop" -Dversion="[version]" -Dpackaging=jar`
* Indiquez dans le `pom.xml` la dernière version :
```xml
<dependency>
<groupId>cn.superiormc</groupId>
<artifactId>ultimateshop</artifactId>
<version>[version]</version>
<scope>provided</scope>
</dependency>
```
* Mettez à jour les dépendances Maven
* Utilisez `mvn clean` et `mvn test` pour nettoyer le projet et vérifier la santé du code
* Exécutez en faisant un `mvn package` et en mettant le plugin dans un serveur de test Spigot ou équivalent

View File

@ -90,12 +90,6 @@
<version>2.21.2</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>cn.superiormc</groupId>
<artifactId>ultimateshop</artifactId>
<version>3.10.2</version>
<scope>provided</scope>
</dependency>
<dependency>
<groupId>junit</groupId>
<artifactId>junit</artifactId>

View File

@ -1,6 +1,7 @@
package fr.molzonas.painfulloss;
import fr.molzonas.painfulloss.commands.PainfulLossCommand;
import fr.molzonas.painfulloss.provider.UltimateShopPriceProvider;
import fr.molzonas.painfulloss.utils.PropertiesEnum;
import fr.molzonas.painfulloss.listeners.DeathListener;
import fr.molzonas.painfulloss.provider.CountPriceProvider;
@ -72,7 +73,13 @@ public final class PainfulLoss extends JavaPlugin {
// Ultimate Shop
Plugin ultimateShop = getServer().getPluginManager().getPlugin("UltimateShop");
if (ultimateShop != null && ultimateShop.isEnabled()) {
info("UltimateShop detected (but inactive for Painful Loss)");
UltimateShopPriceProvider uspp = new UltimateShopPriceProvider(ultimateShop);
if (uspp.isReady()) {
ultimateShopProvider = Optional.of(uspp);
info("UltimateShop detected, prices loaded");
} else {
info("UltimateShop detected, prices unavailable");
}
}
// Essentials

View File

@ -16,4 +16,5 @@ public interface PriceProvider {
}
default boolean isReady() { return true; }
default boolean isCountBased() { return false; }
default void reload() { }
}

View File

@ -1,43 +1,108 @@
package fr.molzonas.painfulloss.provider;
import cn.superiormc.ultimateshop.api.ShopHelper;
import cn.superiormc.ultimateshop.objects.items.AbstractSingleThing;
import cn.superiormc.ultimateshop.objects.items.GiveResult;
import fr.molzonas.painfulloss.PainfulLoss;
import fr.molzonas.painfulloss.utils.PropertiesEnum;
import org.bukkit.Material;
import org.bukkit.configuration.ConfigurationSection;
import org.bukkit.entity.Player;
import org.bukkit.inventory.ItemStack;
import org.bukkit.plugin.Plugin;
import org.jetbrains.annotations.Nullable;
import java.lang.reflect.Method;
import java.math.BigDecimal;
import java.util.Map;
import java.util.Optional;
import java.util.logging.Level;
public class UltimateShopPriceProvider implements PriceProvider {
private final Reflect reflect;
private String economyProvider;
private boolean ready = true;
public UltimateShopPriceProvider(Plugin plugin) {
reload();
this.reflect = Reflect.resolve(plugin);
if (this.reflect == null) {
this.ready = false;
PainfulLoss.log(Level.WARNING, "UltimateShop API not found");
}
}
@Override
public String getName() {
return "UltimateShop";
}
@Override
public boolean isReady() {
return this.ready;
}
@Override
public Optional<Double> getPrice(ItemStack stack, @Nullable Player player) {
if (stack == null || stack.getType() == Material.AIR || stack.getAmount() <= 0) return Optional.empty();
double total = 0d;
GiveResult gr = ShopHelper.getSellPrices(new ItemStack[]{stack}, player, stack.getAmount());
if (gr == null) return Optional.empty();
Map<AbstractSingleThing, BigDecimal> map = gr.getResultMap();
if (map == null || map.isEmpty()) return Optional.empty();
for (Map.Entry<AbstractSingleThing, BigDecimal> entry : map.entrySet()) {
AbstractSingleThing key = entry.getKey();
BigDecimal value = entry.getValue();
ConfigurationSection section = key.getSingleSection();
String econ = section.getString("economy-plugin", "");
if (econ.equalsIgnoreCase(PropertiesEnum.PRICE_PROVIDER.getString())) {
total += value.doubleValue();
try {
return Optional.of(reflect.priceFor(stack, player, economyProvider));
} catch (Exception e) {
return Optional.empty();
}
}
@Override
public void reload() {
economyProvider = PropertiesEnum.ECONOMY_PROVIDER.getString();
}
static final class Reflect {
private static final String SHOPHELPER_CLASSNAME = "cn.superiormc.ultimateshop.api.ShopHelper";
final Method getSellPrices;
final Method giveResultMap;
Method getSingleSection;
Method sectionGetString;
private Reflect(Method sellPrices, Method giveResultMap) {
this.getSellPrices = sellPrices;
this.giveResultMap = giveResultMap;
}
static Reflect resolve(Plugin plugin) {
try {
ClassLoader cl = plugin.getClass().getClassLoader();
Class<?> c = Class.forName(SHOPHELPER_CLASSNAME, false, cl);
Method gp = c.getMethod("getSellPrices", ItemStack[].class, Player.class, int.class);
Class<?> resultClass = gp.getReturnType();
Method getMap = resultClass.getMethod("getResultMap");
return new Reflect(gp, getMap);
} catch (Exception ex) {
return null;
}
}
return total > 0 ? Optional.of(total) : Optional.empty();
double priceFor(ItemStack item, Player player, String economyProvider) throws Exception {
if (item == null || item.getType().isAir() || item.getAmount() <= 0) return 0d;
Object result = getSellPrices.invoke(null, new ItemStack[]{item}, player, item.getAmount());
double total = 0d;
if (result == null) return total;
Map<Object, BigDecimal> map = (Map<Object, BigDecimal>) giveResultMap.invoke(result);
if (map == null || map.isEmpty()) return total;
if (getSingleSection == null) {
Object anyKey = map.keySet().iterator().next();
getSingleSection = anyKey.getClass().getMethod("getSingleSection");
Object sec = getSingleSection.invoke(anyKey);
sectionGetString = sec.getClass().getMethod("getString", String.class, String.class);
}
for (Map.Entry<Object, BigDecimal> entry : map.entrySet()) {
Object section = getSingleSection.invoke(entry.getKey());
String economyPlugin = String.valueOf(sectionGetString.invoke(section, "economy-plugin", ""));
if (!economyPlugin.equalsIgnoreCase(economyProvider)) continue;
BigDecimal value = entry.getValue();
if (value != null) total += entry.getValue().doubleValue();
}
return total;
}
}
}

View File

@ -2,6 +2,7 @@ name: PainfulLoss
version: '1.0'
main: fr.molzonas.painfulloss.PainfulLoss
api-version: '1.20'
prefix: PainfulLoss
softdepend: [Essentials, UltimateShop]
author: Molzonas
commands: