# Architecture V1 ## État et autorité `ShopSavedData` conserve boutiques, réputation par propriétaire et crédits. `ShopInventoryBlockEntity` conserve les objets. `ShopManager` gère les sessions en mémoire sur le thread serveur. Mode, règles et identifiant de session sont immuables ; les commandes sont tarifées à leur création. L’écran reçoit un instantané et envoie des actions de menu, jamais des montants approuvés par le client. `Delivery.consume` vérifie toutes les cases avant de modifier un objet. `ShopManager.finish` retire la commande avant le paiement : un second clic ne peut plus la valider. Cela protège les interactions normales ; il ne s’agit pas d’un journal transactionnel entre fichiers joueur, chunks et SavedData en cas d’arrêt brutal du système. ## Provenance Le composant `ShopProductionData`, persistant et synchronisé, contient boutique, session, producteur, handler et famille. `ShopProductionTracker` définit le contrat commun. Les adaptateurs observent la production réelle. Un addon serveur est du code de confiance : appeler `produced` sans consommer les ingrédients violerait ce contrat. Les mixins Vanilla suivent : - Le contexte de clic, restauré par `try/finally`, et les ingrédients avant consommation. - Les résultats de craft, taille et forge pendant l’extraction ; les prévisualisations perdent ensuite leur marquage. - Les restes de fabrication lors de la consommation réelle, avant restitution dans la grille. - Les lots de four chargés manuellement, les entrées attendues et les opérations successives ; les anciennes sorties et les apports automatiques invalident l’accréditation. Une matière explicitement autorisée peut servir d’ingrédient externe. Un produit livrable exige un marquage de la session courante. Une nouvelle session rend les marquages précédents inutilisables. ## Résolveur et stock `RecipeResolver` est indépendant de Minecraft. Il explore les alternatives sur des copies, détecte les cycles, compte les lots, restes et combustibles. Recherche bornée à 12 niveaux et 12 000 étapes par demande ; échec ou budget épuisé exclut le produit. `ShopStock` compte les conteneurs par identité : stockages, inventaire/cursor du propriétaire dans la zone, véritables entrées de menus, comptoir et stock fourni par les handlers. Les prévisualisations ne comptent pas. Les productions valides disponibles peuvent satisfaire une commande sans refabrication. Les objets à composants particuliers sont exclus du calcul par ID. L’estimation est conservatrice : elle n’optimise pas la chaleur déjà engagée ni l’ordonnancement parallèle des machines. Les durées s’additionnent. Le joueur reste libre d’utiliser toute chaîne admissible, sans recette imposée. Cache de recettes indépendant du mode ; résolveurs partagés par capacités ; quantités recalculées pour chaque commande. Scan complet à la vérification, à l’ouverture ou après invalidation, jamais à chaque tick. Rechargement : fermeture neutre et invalidation des caches. ## Ajouter une intégration Enregistrer avec `ProductionRegistry.register`, à l’initialisation commune : 1. `StationFamilyProvider` : IDs de familles namespacés. 2. `StationProvider` : reconnaissance des blocs, retour `StationDefinition(id, family, handler)` ; `intrinsicStations` pour les capacités sans bloc. 3. `RecipeProvider` : `ProductionRecipe` déterministes. Chaque ensemble d’alternatives consomme **une unité** ; répéter l’ensemble pour plusieurs unités. 4. `ProductionHandler` : validation des entrées et éventuel stock physique des stations. L’adaptateur vérifie propriétaire, présence et station réelle ; observe les ingrédients avant consommation ; appelle `ShopProductionTracker.produced(ProductionContext, inputs, output)` uniquement à la création réelle ; consomme exactement les entrées. Il observe ou refuse les apports automatiques. `reset` abandonne les contextes techniques invalides. Exemple exécutable : `src/gameTest/java/fr/shinuwa/counterofshinuwa/test/TestProductionIntegration.java`. Station cloche, nouvelle famille, recette et handler ajoutés sans branche spécifique dans le cœur. Le mod de test est exclu du JAR distribué. ## Easy NPC Le cœur connaît `NpcAdapter`. `EasyNpcAdapter` crée le type configuré, établit sa propriété et utilise les bulles Easy NPC. Un objectif personnalisé enregistré via son API suit les positions de la boutique avec une précision de chemin de zéro bloc. Core 7.12.1 présente deux particularités : les villageois exigent un objectif de voyage pour bouger ; l’action publique termine son chemin à un bloc de la cible. L’objectif propre au mod permet de suivre précisément les tapis. La navigation est réessayée ; après 600 ticks sans progrès, le client est retiré sans pénalité technique. Les anciens clients sont supprimés à leur rechargement si la session a disparu. Types testés : `easy_npc:humanoid`, `easy_npc:villager`. D’autres types peuvent avoir des dimensions ou comportements incompatibles avec les parcours et nécessitent des essais dédiés.