PageRenderTime 57ms CodeModel.GetById 27ms RepoModel.GetById 0ms app.codeStats 0ms

/src/com/dercd/bukkit/cdapi/PluginHandler.java

https://gitlab.com/Moylle/CDAPI
Java | 912 lines | 701 code | 63 blank | 148 comment | 123 complexity | 5f2a441e723947b7ece222d0796cc33a MD5 | raw file
  1. package com.dercd.bukkit.cdapi;
  2. import java.io.File;
  3. import java.io.UnsupportedEncodingException;
  4. import java.net.URL;
  5. import java.net.URLDecoder;
  6. import java.util.ArrayList;
  7. import java.util.HashMap;
  8. import java.util.List;
  9. import java.util.Map;
  10. import java.util.logging.Logger;
  11. import org.bukkit.Bukkit;
  12. import org.bukkit.permissions.Permission;
  13. import org.bukkit.plugin.Plugin;
  14. import org.bukkit.plugin.PluginManager;
  15. import org.spigotmc.SpigotConfig;
  16. import com.dercd.bukkit.cdapi.annotations.CDInternPluginDepend;
  17. import com.dercd.bukkit.cdapi.annotations.CDPluginDepend;
  18. import com.dercd.bukkit.cdapi.events.CDPluginDisableEvent;
  19. import com.dercd.bukkit.cdapi.events.CDPluginEnableEvent;
  20. import com.dercd.bukkit.cdapi.events.CDPluginLoadEvent;
  21. import com.dercd.bukkit.cdapi.events.CDServerStartedEvent;
  22. import com.dercd.bukkit.cdapi.exceptions.CDGException;
  23. import com.dercd.bukkit.cdapi.exceptions.CDPluginNotFoundException;
  24. import com.dercd.bukkit.cdapi.exceptions.Handleable;
  25. import com.dercd.bukkit.cdapi.listener.CommandListener;
  26. import com.dercd.bukkit.cdapi.listener.EventListener;
  27. import com.dercd.bukkit.cdapi.listener.PacketListener;
  28. import com.dercd.bukkit.cdapi.listener.PluginMessageListener;
  29. import com.dercd.bukkit.cdapi.listener.objects.CDListenerObject;
  30. import com.dercd.bukkit.cdapi.listener.register.CommandRegister;
  31. import com.dercd.bukkit.cdapi.listener.register.EventRegister;
  32. import com.dercd.bukkit.cdapi.listener.register.PacketRegister;
  33. import com.dercd.bukkit.cdapi.listener.register.PluginMessageRegister;
  34. import com.dercd.bukkit.cdapi.tools.DynamicClassLoader;
  35. import com.dercd.bukkit.cdapi.tools.DynamicDependencyClassLoader;
  36. import com.dercd.bukkit.cdapi.tools.Log;
  37. import com.dercd.bukkit.cdapi.tools.minecraft.NameFetcher;
  38. import com.dercd.bukkit.cdapi.tools.minecraft.UUIDFetcher;
  39. import com.dercd.bukkit.plugins.EMStop;
  40. import com.google.common.collect.ImmutableMap;
  41. /**
  42. * Class which handles all actions with CDPlugins
  43. *
  44. * @author DerCD
  45. */
  46. public class PluginHandler
  47. {
  48. private CDAPI cdapi;
  49. protected Logger log = Logger.getLogger("Minecraft");
  50. protected Log clog;
  51. protected EventListener elistener;
  52. protected PacketListener plistener;
  53. protected CommandListener clistener;
  54. protected PluginMessageListener pmlistener;
  55. protected boolean isLoaded = false;
  56. protected boolean isEnabled = false;
  57. protected boolean isInitialized = false;
  58. protected DynamicClassLoader<CDPlugin> classLoader;
  59. protected NameFetcher nameFetcher;
  60. protected UUIDFetcher uuidFetcher;
  61. public Map<String, Class<? extends CDPlugin>> pluginClasses = new HashMap<String, Class<? extends CDPlugin>>();
  62. public Map<Class<? extends CDPlugin>, CDPlugin> plugins = new HashMap<Class<? extends CDPlugin>, CDPlugin>();
  63. protected CommandRegister cRegister;
  64. protected EventRegister eRegister;
  65. protected PacketRegister pRegister;
  66. protected PluginMessageRegister pmRegister;
  67. protected double[] startTimes = new double[3];
  68. protected ThreadGroup threadGroup = new ThreadGroup("CDAPI-ThreadGroup");
  69. protected boolean spigot = false, bungeeCord = false;
  70. protected PluginHandler(CDAPI cdapi)
  71. {
  72. this.cdapi = cdapi;
  73. initialize();
  74. getSpigot();
  75. }
  76. /**
  77. * @return The CDAPI-Object associated with this handler
  78. */
  79. public CDAPI getMain()
  80. {
  81. return this.cdapi;
  82. }
  83. /**
  84. * Initialize one CDPlugin
  85. *
  86. * @param c Class extending CDPlugin to initialize
  87. */
  88. public void initialize(Class<? extends CDPlugin> c) throws IllegalArgumentException, ReflectiveOperationException, SecurityException
  89. {
  90. if (!this.plugins.containsKey(c)) return;
  91. if (this.plugins.get(c) != null) return;
  92. CDPlugin cdp = c.getConstructor(PluginHandler.class).newInstance(this);
  93. this.plugins.put(c, cdp);
  94. this.pluginClasses.put(cdp.getName(), c);
  95. }
  96. private void initialize()
  97. {
  98. this.clog = new Log(CDPlugin.getDir() + "logs", this);
  99. this.elistener = new EventListener(this);
  100. this.plistener = new PacketListener(this);
  101. this.clistener = new CommandListener(this);
  102. this.pmlistener = new PluginMessageListener(this);
  103. }
  104. private void getSpigot()
  105. {
  106. try
  107. {
  108. this.bungeeCord = SpigotConfig.bungee;
  109. this.spigot = true;
  110. }
  111. catch(Throwable t) { }
  112. }
  113. private void initializeAfterConstructed()
  114. {
  115. this.nameFetcher = new NameFetcher();
  116. this.uuidFetcher = new UUIDFetcher();
  117. this.nameFetcher.setUUIDFetcher(this.uuidFetcher);
  118. this.uuidFetcher.setNameFetcher(this.nameFetcher);
  119. this.cRegister = new CommandRegister(this.cdapi);
  120. this.eRegister = new EventRegister(this.cdapi);
  121. this.pRegister = new PacketRegister(this.cdapi);
  122. this.pmRegister = new PluginMessageRegister(this.cdapi);
  123. this.isInitialized = true;
  124. }
  125. private void uninitialize()
  126. {
  127. unregisterPermissions();
  128. this.cRegister.unregisterBukkitCommands();
  129. this.pRegister.unregisterProtocolLibPackets();
  130. this.eRegister.unregisterBukkitEvents();
  131. this.pmRegister.unregisterMessageChannels();
  132. this.plugins.clear();
  133. this.pluginClasses.clear();
  134. Bukkit.getScheduler().cancelTasks(this.cdapi);
  135. this.elistener = null;
  136. this.plistener = null;
  137. this.clistener = null;
  138. this.pmlistener = null;
  139. this.isEnabled = false;
  140. this.cRegister = null;
  141. this.pRegister = null;
  142. this.eRegister = null;
  143. DynamicClassLoader.createdClassLoader = null;
  144. DynamicDependencyClassLoader.excluded.clear();
  145. System.gc();
  146. this.isInitialized = false;
  147. }
  148. private void uninitialize(CDPlugin cdp)
  149. {
  150. this.plugins.put(cdp.getClass(), null);
  151. cdp = null;
  152. System.gc();
  153. }
  154. private void deregister(CDPlugin cdp)
  155. {
  156. this.cRegister.unregisterPlugin(cdp);
  157. this.pRegister.unregisterPlugin(cdp);
  158. this.eRegister.unregisterPlugin(cdp);
  159. this.pmRegister.unregisterPlugin(cdp);
  160. }
  161. /**
  162. * Reloads one CDPlugin
  163. *
  164. * @param cdp CDPlugin to reload
  165. * @throws ReflectiveOperationException
  166. */
  167. public void reload(CDPlugin cdp) throws IllegalArgumentException, SecurityException, ReflectiveOperationException
  168. {
  169. String name = cdp.getName();
  170. this.log.info("[CDAPI] Disabling " + name);
  171. disable(cdp);
  172. this.log.info("[CDAPI] Initializing " + name);
  173. initialize(cdp.getClass());
  174. // cdp = cdp.getClass().getConstructor(PluginHandler.class).newInstance(this);
  175. // this.plugins.put(cdp.getClass(), cdp);
  176. cdp = this.plugins.get(cdp.getClass());
  177. this.log.info("[CDAPI] Loading " + name);
  178. load(cdp);
  179. this.log.info("[CDAPI] Enabling " + name);
  180. enable(cdp);
  181. this.log.info("[CDAPI] Reload done " + name);
  182. }
  183. /**
  184. * Reloads all registered CDPlugins
  185. */
  186. public void reload()
  187. {
  188. this.log.info("[CDAPI] Disabling");
  189. disable();
  190. this.log.info("[CDAPI] Initializing");
  191. initialize();
  192. this.log.info("[CDAPI] Loading");
  193. load();
  194. this.log.info("[CDAPI] Enabling");
  195. enable();
  196. this.log.info("[CDAPI] Reload done");
  197. }
  198. /**
  199. * Loads one CDPlugin
  200. *
  201. * @param cdp The CDPlugin to load
  202. */
  203. public void load(CDPlugin cdp)
  204. {
  205. if (cdp.isLoaded) return;
  206. registerPermissions(cdp);
  207. this.cRegister.searchCommands(cdp, false);
  208. this.eRegister.searchEvents(cdp);
  209. this.pRegister.searchPackets(cdp);
  210. this.pmRegister.searchChannels(cdp);
  211. setDependPlugins(cdp, Bukkit.getPluginManager().getPlugins());
  212. CDPluginLoadEvent e = new CDPluginLoadEvent();
  213. this.clog.log("Loading plugin " + cdp.getName(), this);
  214. this.elistener.callEvent(e, cdp.getClass());
  215. if(e.isSuccessSet(cdp) || e.getSuccess(cdp))
  216. this.clog.log("Enabling of plugin " + cdp.getName() + " successfull", this);
  217. else
  218. this.clog.log("Enabling of plugin " + cdp.getName() + " unsuccessfull", this);
  219. cdp.isLoaded = true;
  220. this.clog.log("Plugin " + cdp.getName() + " loaded", this);
  221. }
  222. /**
  223. * Loads all registered CDPlugins
  224. */
  225. public void load()
  226. {
  227. long currentTime = System.currentTimeMillis();
  228. initializeAfterConstructed();
  229. this.clistener.registerAReceive();
  230. try
  231. {
  232. loadClasses();
  233. }
  234. catch (Exception x)
  235. {
  236. this.clog.printException(x);
  237. return;
  238. }
  239. doDirectorys();
  240. this.eRegister.searchEvents();
  241. this.eRegister.registerBukkitEvents(false);
  242. this.pRegister.searchPackets();
  243. this.pRegister.registerProtocolLibPackets(false);
  244. this.cRegister.searchCommands(false);
  245. this.pmRegister.searchChannels();
  246. this.pmRegister.registerPluginMessageChannels(false);
  247. registerPermissions();
  248. setDependPlugins();
  249. this.clog.log("Calling LoadEvent", this);
  250. CDPluginLoadEvent e = new CDPluginLoadEvent();
  251. this.elistener.onEvent(e);
  252. int failed = 0;
  253. for (boolean success : e.getSuccess())
  254. if (!success) failed++;
  255. this.clog.log((e.getSuccess().size() - failed) + " intern Plugins catched and processed the LoadEvent successfully, " + failed + " failed", this);
  256. if (failed != 0) this.log.warning(failed + " Plugins failed to load");
  257. this.isLoaded = true;
  258. for(CDPlugin cdp : this.plugins.values())
  259. cdp.isLoaded = true;
  260. this.clog.log("Plugins loaded", this);
  261. this.startTimes[0] = System.currentTimeMillis() - currentTime;
  262. this.clog.log("Needed " + this.startTimes[0] / 1000 + " seconds to load", this);
  263. }
  264. /**
  265. * Enables one CDPlugin
  266. *
  267. * @param cdp The CDPlugin to enable
  268. */
  269. public void enable(CDPlugin cdp)
  270. {
  271. if (cdp.isEnabled || !cdp.isLoaded) return;
  272. CDPluginEnableEvent e = new CDPluginEnableEvent();
  273. this.clog.log("Enabling plugin " + cdp.getClass().getSimpleName(), this);
  274. this.elistener.callEvent(e, cdp.getClass());
  275. cdp.isEnabled = true;
  276. CDServerStartedEvent e2 = new CDServerStartedEvent();
  277. this.elistener.callEvent(e2, cdp.getClass());
  278. if((!e.isSuccessSet(cdp) || e.getSuccess(cdp)) && (e2.isSuccessSet(cdp) || e2.getSuccess(cdp)))
  279. this.clog.log("Enabling of plugin " + cdp.getName() + " successfull", this);
  280. else
  281. this.clog.log("Enabling of plugin " + cdp.getName() + " unsuccessfull", this);
  282. this.clog.log("Plugin " + cdp.getClass().getSimpleName() + " enabled", this);
  283. }
  284. /**
  285. * Enables all registered CDPlugins
  286. */
  287. public void enable()
  288. {
  289. long currentTime = System.currentTimeMillis();
  290. if (!this.isInitialized)
  291. {
  292. initialize();
  293. initializeAfterConstructed();
  294. }
  295. this.clog.log("Enabling", this);
  296. this.clog.log("Calling EnableEvent", this);
  297. CDPluginEnableEvent e = new CDPluginEnableEvent();
  298. this.elistener.onEvent(e);
  299. int failed = 0;
  300. for (boolean success : e.getSuccess())
  301. if (!success) failed++;
  302. this.clog.log((e.getSuccess().size() - failed) + " Plugins catched and processed the EnableEvent successfully, " + failed + " failed", this);
  303. if (failed != 0) this.log.warning(failed + " Plugins failed to enable");
  304. Bukkit.getScheduler().scheduleSyncDelayedTask(this.cdapi, () ->
  305. {
  306. PluginHandler.this.eRegister.registerBukkitEvents(true);
  307. PluginHandler.this.pRegister.registerProtocolLibPackets(true);
  308. PluginHandler.this.pmRegister.registerPluginMessageChannels(true);
  309. PluginHandler.this.cRegister.registerBukkitCommands();
  310. serverStarted();
  311. }, 0);
  312. this.clog.log("Plugins enabled", this);
  313. this.isEnabled = true;
  314. for(CDPlugin cdp : this.plugins.values())
  315. cdp.isEnabled = true;
  316. this.startTimes[1] = System.currentTimeMillis() - currentTime;
  317. this.clog.log("Needed " + this.startTimes[1] / 1000 + " seconds to enable", this);
  318. }
  319. void serverStarted()
  320. {
  321. this.clog.log("Calling ServerStartedEvent", this);
  322. CDServerStartedEvent e = new CDServerStartedEvent();
  323. this.elistener.onEvent(e);
  324. int failed = 0;
  325. for (boolean success : e.getSuccess())
  326. if (!success) failed++;
  327. this.clog.log((e.getSuccess().size() - failed) + " Plugins catched and processed the ServerStartedEvent successfully, " + failed + " failed", this);
  328. }
  329. /**
  330. *
  331. * @return If this server runs Spigot
  332. */
  333. public boolean isSpigot()
  334. {
  335. return this.spigot;
  336. }
  337. /**
  338. *
  339. * @return If this server uses BungeeCord
  340. */
  341. public boolean isBungeeCord()
  342. {
  343. return this.bungeeCord;
  344. }
  345. /**
  346. * @param name The name of the CDPlugin. If an registered CDPlugin is null
  347. * its class-name, otherwise the name given by the
  348. * CDPlugin.getName()-method
  349. * @return The CDPlugin if found, otherwise null
  350. * @throws CDPluginNotFoundException
  351. */
  352. public CDPlugin getPlugin(String name) throws CDPluginNotFoundException
  353. {
  354. CDPlugin cdp = null;
  355. boolean found = false;
  356. for(CDPlugin c : this.plugins.values())
  357. if(c != null)
  358. if(c.getName().equals(name))
  359. return c;
  360. else if(c.getName().equalsIgnoreCase(name))
  361. {
  362. cdp = c;
  363. found = true;
  364. }
  365. if(found) return cdp;
  366. for (Class<? extends CDPlugin> c : this.plugins.keySet())
  367. if(c.getSimpleName().equals(name) || c.getName().equals(name))
  368. return this.plugins.get(c);
  369. else if(c.getSimpleName().equalsIgnoreCase(name) || c.getName().equalsIgnoreCase(name))
  370. {
  371. cdp = this.plugins.get(c);
  372. found = true;
  373. }
  374. if(found) return cdp;
  375. throw new CDPluginNotFoundException(name);
  376. }
  377. public Class<? extends CDPlugin> getPluginClass(String name) throws CDPluginNotFoundException
  378. {
  379. Class<? extends CDPlugin> clazz;
  380. clazz = this.pluginClasses.get(name);
  381. if(clazz != null) return clazz;
  382. for(String pluginName : this.pluginClasses.keySet())
  383. if(name.equalsIgnoreCase(pluginName))
  384. return this.pluginClasses.get(pluginName);
  385. for(Class<? extends CDPlugin> c : this.pluginClasses.values())
  386. if(c != null)
  387. if(c.getSimpleName().equals(name) || c.getName().equals(name))
  388. return c;
  389. else if(c.getSimpleName().equalsIgnoreCase(name) || c.getName().equals(name))
  390. clazz = c;
  391. if(clazz != null) return clazz;
  392. throw new CDPluginNotFoundException(name);
  393. }
  394. /**
  395. * @param clazz The class of an registered CDPlugin
  396. * @return The CDPlugin if found, otherwise null
  397. */
  398. @SuppressWarnings("unchecked")
  399. public <CDP> CDP getPlugin(Class<CDP> clazz)
  400. {
  401. return (CDP) this.plugins.get(clazz);
  402. }
  403. private void loadClasses() throws IllegalArgumentException, SecurityException, UnsupportedEncodingException
  404. {
  405. this.clog.log("Clearing Plugins", this);
  406. this.plugins.clear();
  407. this.clog.log("Finding Plugins and calling Constructors of it", this);
  408. this.classLoader = new DynamicDependencyClassLoader<CDPlugin>(this.clog);
  409. URL cFile = this.cdapi.getClass().getProtectionDomain().getCodeSource().getLocation();
  410. DynamicClassLoader.preCreatedClassLoaders.put(cFile, this.cdapi.getClass().getClassLoader());
  411. for (CDPlugin cdp : this.classLoader.loadFiles(new File[] { new File(CDPlugin.getDir()), new File(URLDecoder.decode(cFile.getPath(), "UTF-8")) }, CDPlugin.class, new Class<?>[] { PluginHandler.class }, this))
  412. {
  413. this.plugins.put(cdp.getClass(), cdp);
  414. this.pluginClasses.put(cdp.getName(), cdp.getClass());
  415. }
  416. this.clog.log("Found " + this.plugins.size() + " CDPlugins", this);
  417. this.clog.log("Done", this);
  418. }
  419. private void doDirectorys()
  420. {
  421. this.clog.log("Checking and creating Directorys", this);
  422. checkDir(CDPlugin.getDir());
  423. String[] paths;
  424. for (CDPlugin cdp : this.plugins.values())
  425. if ((paths = cdp.getDirectorys()) != null) for (String path : paths)
  426. checkDir(CDPlugin.getDir() + path);
  427. this.clog.log("All Directorys checked", this);
  428. }
  429. public void unregisterPermissions(CDPlugin cdp)
  430. {
  431. PluginManager manager = Bukkit.getPluginManager();
  432. this.clog.log("Unregister Permissions for " + cdp.getClass().getName(), this);
  433. for (Permission perm : cdp.getPermissions())
  434. manager.removePermission(perm);
  435. }
  436. private void unregisterPermissions()
  437. {
  438. this.clog.log("Unregister Permission", this);
  439. PluginManager manager = Bukkit.getPluginManager();
  440. for (CDPlugin cdp : this.plugins.values())
  441. if(cdp != null)
  442. for (Permission perm : cdp.getPermissions())
  443. manager.removePermission(perm);
  444. this.clog.log("All Permissions unregistered", this);
  445. }
  446. /**
  447. * Registers all in the CDPlugin listed permissions to Bukkit
  448. *
  449. * @param cdp The CDPlugin to lookup the permissions
  450. */
  451. public void registerPermissions(CDPlugin cdp)
  452. {
  453. PluginManager manager = Bukkit.getPluginManager();
  454. this.clog.log("Register Permissions for " + cdp.getClass().getName(), this);
  455. for (Permission perm : cdp.getPermissions())
  456. manager.addPermission(perm);
  457. }
  458. private void registerPermissions()
  459. {
  460. this.clog.log("Register Permissions", this);
  461. PluginManager manager = Bukkit.getPluginManager();
  462. for (CDPlugin p : this.plugins.values())
  463. for (Permission perm : p.getPermissions())
  464. try
  465. {
  466. manager.addPermission(perm);
  467. }
  468. catch (Exception x)
  469. {
  470. this.clog.log("Error while registering Permission " + perm.getName(), this);
  471. }
  472. this.clog.log("All Permissions registered", this);
  473. }
  474. /**
  475. * Disables one CDPlugin
  476. *
  477. * @param cdp The CDPlugin to disable
  478. */
  479. public void disable(CDPlugin cdp)
  480. {
  481. if (!cdp.isEnabled) return;
  482. unregisterPermissions(cdp);
  483. CDPluginDisableEvent e = new CDPluginDisableEvent();
  484. this.clog.log("Deregistering plugin " + cdp.getClass().getSimpleName(), this);
  485. deregister(cdp);
  486. this.clog.log("Plugin " + cdp.getClass().getSimpleName() + " deregistered", this);
  487. this.clog.log("Disabling plugin " + cdp.getClass().getSimpleName(), this);
  488. this.elistener.callEvent(e, cdp.getClass());
  489. cdp.isEnabled = false;
  490. this.clog.log("Plugin " + cdp.getClass().getSimpleName() + " disabled", this);
  491. this.clog.log("Interrupting all Threads in the plugins ThreadGroup", this);
  492. try
  493. {
  494. cdp.getPluginThreadGroup().interrupt();
  495. this.clog.log("All Threads in the ThreadGroup interrupted", this);
  496. }
  497. catch (SecurityException x) { this.clog.log("SecurityException while interrupting Threads. No Thread was interrupted", this); }
  498. this.clog.log("Uninitializing plugin " + cdp.getClass().getSimpleName(), this);
  499. uninitialize(cdp);
  500. cdp.isLoaded = false;
  501. this.clog.log("Plugin " + cdp.getClass().getSimpleName() + " uninitialized", this);
  502. }
  503. /**
  504. * Disables all listed CDPlugins
  505. */
  506. public void disable()
  507. {
  508. long currentTime = System.currentTimeMillis();
  509. this.clog.log("Calling DisableEvent", this);
  510. CDPluginDisableEvent e = new CDPluginDisableEvent();
  511. this.elistener.onEvent(e);
  512. int failed = 0;
  513. for (boolean success : e.getSuccess())
  514. if (!success) failed++;
  515. this.clog.log((e.getSuccess().size() - failed) + " Plugins catched and processed the DisableEvent successfully, " + failed + " failed", this);
  516. if (failed != 0)
  517. {
  518. this.log.warning(failed + " Plugins failed to disable");
  519. this.log.warning("Maybe data isn't save");
  520. }
  521. else this.clog.log("Plugins disabled", this);
  522. for(CDPlugin cdp : this.plugins.values())
  523. {
  524. if(cdp == null) continue;
  525. cdp.isLoaded = false;
  526. cdp.isEnabled = false;
  527. }
  528. this.clog.log("Interrupting all Threads in the CDAPI ThreadGroup", this);
  529. try
  530. {
  531. this.threadGroup.interrupt();
  532. this.clog.log("All Threads in the ThreadGroup interrupted", this);
  533. }
  534. catch (SecurityException x) { this.clog.log("SecurityException while interrupting Threads. No Thread was interrupted", this); }
  535. this.clog.log("Unitialize CDAPI", this);
  536. uninitialize();
  537. this.clog.log("Done", this);
  538. this.startTimes[2] = System.currentTimeMillis() - currentTime;
  539. this.clog.log("Needed " + this.startTimes[2] / 1000 + " seconds to disable", this);
  540. this.clog.close();
  541. this.clog = null;
  542. System.gc();
  543. }
  544. /**
  545. * Checks for all listed CDPlugin the directorys given by the
  546. * CDPlugin.getDirectorys()-method
  547. * <p>
  548. * if they existing. If not it would be created
  549. *
  550. * @param path
  551. */
  552. public void checkDir(String path)
  553. {
  554. this.clog.log("Checking Directory " + path, this);
  555. File f = new File(path);
  556. if (!f.exists())
  557. {
  558. this.clog.log("Not existing. Creating it", this);
  559. f.mkdirs();
  560. }
  561. else this.clog.log("Existing", this);
  562. }
  563. /**
  564. * Universial method used by the listeners to unregister all listed
  565. * refereces
  566. *
  567. * @param cdp The CDPlugin to unregister
  568. * @param map The Map to unregister from
  569. */
  570. public static void unregisterPlugin(CDPlugin cdp, Map<String, List<CDListenerObject>> map)
  571. {
  572. List<CDListenerObject> toRemove = new ArrayList<CDListenerObject>();
  573. List<CDListenerObject> val;
  574. for (String key : new HashMap<String, List<CDListenerObject>>(map).keySet())
  575. {
  576. toRemove.clear();
  577. val = map.get(key);
  578. for (CDListenerObject o : new ArrayList<CDListenerObject>(val))
  579. if (o.getObject() == cdp) toRemove.add(o);
  580. if (toRemove.isEmpty()) continue;
  581. val.removeAll(toRemove);
  582. if (val.isEmpty()) map.remove(key);
  583. else map.put(key, val);
  584. }
  585. }
  586. private void setDependPlugins()
  587. {
  588. this.clog.log("Setting (soft-)depend plugins for CDPlugins", this);
  589. PluginManager pm = Bukkit.getPluginManager();
  590. Plugin[] bukkitPlugins = pm.getPlugins();
  591. for (CDPlugin cdp : this.plugins.values())
  592. {
  593. setDependPlugins(cdp, bukkitPlugins);
  594. setDependCDPlugins(cdp);
  595. }
  596. this.clog.log("Done", this);
  597. }
  598. private void setDependCDPlugins(CDPlugin cdp)
  599. {
  600. CDInternPluginDepend pd = cdp.getClass().getAnnotation(CDInternPluginDepend.class);
  601. Map<Class<? extends CDPlugin>, CDPlugin> depends = new HashMap<Class<? extends CDPlugin>, CDPlugin>();
  602. Map<String, CDPlugin> softdepends = new HashMap<String, CDPlugin>();
  603. if (pd != null)
  604. {
  605. for (Class<? extends CDPlugin> c : pd.depends())
  606. for (CDPlugin p : this.plugins.values())
  607. if (p.getClass() == c)
  608. {
  609. depends.put(c, p);
  610. break;
  611. }
  612. for (String s : pd.softdepends())
  613. for (CDPlugin p : this.plugins.values())
  614. if (p.getName().equals(s))
  615. {
  616. softdepends.put(s, p);
  617. break;
  618. }
  619. }
  620. cdp.setCDDepend_DO_NOT_USE(ImmutableMap.copyOf(depends));
  621. cdp.setCDSoftDepend_DO_NOT_USE(ImmutableMap.copyOf(softdepends));
  622. }
  623. private void setDependPlugins(CDPlugin cdp, Plugin[] plugins)
  624. {
  625. CDPluginDepend pd = cdp.getClass().getAnnotation(CDPluginDepend.class);
  626. Map<Class<? extends Plugin>, Plugin> depends = new HashMap<Class<? extends Plugin>, Plugin>();
  627. Map<String, Plugin> softdepends = new HashMap<String, Plugin>();
  628. if (pd != null)
  629. {
  630. for (Class<? extends Plugin> c : pd.depends())
  631. for (Plugin p : plugins)
  632. if (p.getClass() == c)
  633. {
  634. depends.put(c, p);
  635. break;
  636. }
  637. for (String s : pd.softdepends())
  638. for (Plugin p : plugins)
  639. if (p.getName().equals(s))
  640. {
  641. softdepends.put(s, p);
  642. break;
  643. }
  644. }
  645. cdp.setDepend_DO_NOT_USE(ImmutableMap.copyOf(depends));
  646. cdp.setSoftDepend_DO_NOT_USE(ImmutableMap.copyOf(softdepends));
  647. }
  648. public int getInitializedPlugins()
  649. {
  650. int i = 0;
  651. for(CDPlugin cdp : this.plugins.values())
  652. if(cdp != null) i++;
  653. return i;
  654. }
  655. public int getLoadedPlugins()
  656. {
  657. int i = 0;
  658. for(CDPlugin cdp : this.plugins.values())
  659. if(cdp != null && cdp.isLoaded) i++;
  660. return i;
  661. }
  662. public int getEnabledPlugins()
  663. {
  664. int i = 0;
  665. for(CDPlugin cdp : this.plugins.values())
  666. if(cdp != null && cdp.isEnabled) i++;
  667. return i;
  668. }
  669. public int getDisabledPlugins()
  670. {
  671. int i = 0;
  672. for(CDPlugin cdp : this.plugins.values())
  673. if(cdp == null) i++;
  674. return i;
  675. }
  676. /**
  677. * Try to handle a CDGException
  678. *
  679. * @param x The CDGException to handle
  680. */
  681. public void throwException(CDGException x)
  682. {
  683. x.handle();
  684. }
  685. /**
  686. *
  687. * @param x The exception to be handled
  688. * @param wasHandled If the exception was already tried to handle
  689. */
  690. public void handleException(Throwable x, boolean wasHandled, CDPlugin cdp)
  691. {
  692. try
  693. {
  694. if (x == null) return;
  695. if (wasHandled)
  696. {
  697. this.clog.printException(x);
  698. this.clog.error("Error while handling something. Exceptions should has been logged", this);
  699. performErrorAction(cdp);
  700. }
  701. else if (x instanceof Handleable) ((Handleable) x).handle();
  702. else handleException(x, true, cdp);
  703. }
  704. catch (Throwable ex)
  705. {
  706. handleException(ex, false, cdp);
  707. }
  708. }
  709. public void performErrorAction(CDPlugin cdp)
  710. {
  711. String msg = "An non-Handleable exception was thrown. Because of the ErrorAction of the CDPlugin ";
  712. switch(cdp.getErrorAction())
  713. {
  714. case DISABLE:
  715. this.clog.log(msg + cdp.getName() + " the plugin will now be disabled", this);
  716. disable(cdp);
  717. return;
  718. case KILL:
  719. this.clog.log(msg + cdp.getName() + " the server process will now be killed (only on Linux)", this);
  720. EMStop.kill();
  721. return;
  722. case NONE:
  723. return;
  724. case SHUTDOWN:
  725. this.clog.log(msg + cdp.getName() + " the server will now be shut down", this);
  726. Bukkit.shutdown();
  727. return;
  728. }
  729. }
  730. /**
  731. * @return The Logger used by the server
  732. */
  733. public Logger getLog()
  734. {
  735. return this.log;
  736. }
  737. /**
  738. * @return The Logger used by the CDAPI
  739. */
  740. public Log getCLog()
  741. {
  742. return this.clog;
  743. }
  744. /**
  745. * @return The intern EventListener
  746. */
  747. public EventListener getEventListener()
  748. {
  749. return this.elistener;
  750. }
  751. /**
  752. * @return The intern PacketListener
  753. */
  754. public PacketListener getPacketListener()
  755. {
  756. return this.plistener;
  757. }
  758. /**
  759. * @return The intern CommandListener
  760. */
  761. public CommandListener getCommandListener()
  762. {
  763. return this.clistener;
  764. }
  765. /**
  766. * @return The intern PluginMessageListener
  767. */
  768. public PluginMessageListener getPluginMessageListener()
  769. {
  770. return this.pmlistener;
  771. }
  772. /**
  773. * @return If the Plugins are loaded
  774. */
  775. public boolean isLoaded()
  776. {
  777. return this.isLoaded;
  778. }
  779. /**
  780. * @return If the Plugins are enabled
  781. */
  782. public boolean isEnabled()
  783. {
  784. return this.isEnabled;
  785. }
  786. /**
  787. * @return If the Plugins are initialized
  788. */
  789. public boolean isInitialized()
  790. {
  791. return this.isInitialized;
  792. }
  793. /**
  794. * @return The intern ClassLoader
  795. */
  796. public DynamicClassLoader<CDPlugin> getClassLoader()
  797. {
  798. return this.classLoader;
  799. }
  800. /**
  801. * @return The intern NameFetcher
  802. */
  803. public NameFetcher getNameFetcher()
  804. {
  805. return this.nameFetcher;
  806. }
  807. /**
  808. * @return The intern UUIDFetcher
  809. */
  810. public UUIDFetcher getUUIDFetcher()
  811. {
  812. return this.uuidFetcher;
  813. }
  814. /**
  815. * @return The intern CommandRegister
  816. */
  817. public CommandRegister getCommandRegister()
  818. {
  819. return this.cRegister;
  820. }
  821. /**
  822. * @return The intern EventRegister
  823. */
  824. public EventRegister getEventRegister()
  825. {
  826. return this.eRegister;
  827. }
  828. /**
  829. * @return The intern PacketRegister
  830. */
  831. public PacketRegister getPacketRegister()
  832. {
  833. return this.pRegister;
  834. }
  835. /**
  836. * @return The intern PluginMessageRegister
  837. */
  838. public PluginMessageRegister getPluginMessageRegister()
  839. {
  840. return this.pmRegister;
  841. }
  842. /**
  843. * @return The CDAPI ThreadGroup
  844. */
  845. public ThreadGroup getThreadGroup()
  846. {
  847. return this.threadGroup;
  848. }
  849. }