swarfarm_parser 42 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468469470471472473474475476477478479480481482483484485486487488489490491492493494495496497498499500501502503504505506507508509510511512513514515516517518519520521522523524525526527528529530531532533534535536537538539540541542543544545546547548549550551552553554555556557558559560561562563564565566567568569570571572573574575576577578579580581582583584585586587588589590591592593594595596597598599600601602603604605606607608609610611612613614615616617618619620621622623624625626627628629630631632633634635636637638639640641642643644645646647648649650651652653654655656657658659660661662663664665666667668669670671672673674675676677678679680681682683684685686687688689690691692693694695696697698699700701702703704705706707708709710711712713714715716717718719720721722723724725726727728729730731732733734735736737738739740741742743744745746747748749750751752753754755756757758759760761762763764765766767768769770771772773774775776777778779780781782783784785786787788789790791792793794795796797798799800801802803804805806807808809810811812813814815816817818819820821822823824825826827828829830831832833834835836837838839840841842843844845846847848849850851852853854855856857858859860861862863864865866867868869870871872873874875876877878879880881882883884885886887888889890891892893894895896897898899900901902903904905906907908909910911912913914915916917
  1. #!/bin/php
  2. <?php
  3. /**
  4. * Swarfarm data parser
  5. *
  6. * Script that parses game data from swarfarm.com.
  7. *
  8. * @author Iñigo Valentin <i@inigovalentin.com>
  9. * @license https://www.gnu.org/licenses/gpl-3.0.en.html GNU General Public License V3
  10. * @package SWDB
  11. */
  12. /**
  13. * Swarfarm URL of the monster list (first page).
  14. */
  15. CONST URL_UNIT = 'https://swarfarm.com/api/v2/monsters/';
  16. /**
  17. * Swarfarm URL of the skill list (first page).
  18. */
  19. CONST URL_SKILL = 'https://swarfarm.com/api/v2/skills/';
  20. /**
  21. * Path to the application
  22. */
  23. CONST PATH = __DIR__ . "/../";
  24. /*
  25. * Script verbosity
  26. *
  27. * 0: Critical
  28. * 1: Error
  29. * 2: Warning
  30. * 3: Info
  31. * 4: Debug
  32. * 5: Trace
  33. */
  34. $args = array(
  35. "verbosity" => 3,
  36. "override_images" => false,
  37. "skip_downloads" => false,
  38. "only_downloads" => false,
  39. "only_new" => false
  40. );
  41. /**
  42. * Echoes an output message to stdout, depending on the verbosity level.
  43. *
  44. * @param int $level Message priority.
  45. * @param string $message content.
  46. */
  47. function output($level, $message, $keep_format = false){
  48. global $args;
  49. if ($level <= $args["verbosity"]){
  50. if ($keep_format == false){
  51. $message = str_replace("\n", " ", $message);
  52. while (strpos($message, " ") !== false){
  53. $message = str_replace(" ", " ", $message);
  54. }
  55. }
  56. if (substr($message, -1) != PHP_EOL && $keep_format == false){
  57. $message .= PHP_EOL;
  58. }
  59. echo $message;
  60. }
  61. }
  62. /**
  63. * Downloads a file.
  64. *
  65. * @param string $url The file to download.
  66. * @param string $target File destination.
  67. * @return boolean true on success, false on error.
  68. */
  69. function download($url, $target){
  70. global $args;
  71. if ($args["skip_downloads"] == true){
  72. return true;
  73. }
  74. if (!file_exists($target) || $args["override_images"] == true){
  75. output(4, "Downloading file '$url' to: '$target'");
  76. if (!file_put_contents($target, file_get_contents($url))) {
  77. output(1, "Error downloading file '$url' to: '$target'");
  78. return false;
  79. }
  80. else{
  81. return true;
  82. }
  83. }
  84. else{
  85. return true;
  86. }
  87. }
  88. /**
  89. * Gets an entity com2us_id from it's Swarfarm id.
  90. *
  91. * @param int $swarfarm_id Entity's Swarfarm ID.
  92. * @return int Entity's com2us_id, -1 on error.
  93. */
  94. function get_com2us_id($swarfarm_id){
  95. if ($swarfarm_id == null){
  96. return null;
  97. }
  98. $contents = file_get_contents(URL_UNIT . $swarfarm_id . "/");
  99. if($contents === false){
  100. //Print out the contents.
  101. output(1, "Unable to retrieve monster.");
  102. return -1;
  103. }
  104. $contents = json_decode($contents);
  105. return $contents->com2us_id;
  106. }
  107. /**
  108. * Gets an element ID from it's name
  109. *
  110. * @param string $name Element name (case insensitive).
  111. * @return int Element ID, -1 on unknown element.
  112. */
  113. function get_element_id($name){
  114. $id = -1;
  115. switch (strtoupper($name)){
  116. case "MAGIC":
  117. $id = 0;
  118. break;
  119. case "WATER":
  120. $id = 1;
  121. break;
  122. case "FIRE":
  123. $id = 2;
  124. break;
  125. case "WIND":
  126. $id = 3;
  127. break;
  128. case "LIGHT":
  129. $id = 4;
  130. break;
  131. case "DARK":
  132. $id = 5;
  133. break;
  134. case "PURE":
  135. $id = 6;
  136. break;
  137. }
  138. return $id;
  139. }
  140. /**
  141. * Gets an archetype ID from it's name
  142. *
  143. * @param string $name Archetype name (case insensitive).
  144. * @return int Archetype ID, -1 on unknown archetype.
  145. */
  146. function get_archetype_id($name){
  147. $id = 0; // NONE
  148. switch (strtoupper($name)){
  149. case "ATTACK":
  150. $id = 1;
  151. break;
  152. case "DEFENSE":
  153. $id = 2;
  154. break;
  155. case "HP":
  156. $id = 3;
  157. break;
  158. case "SUPPORT":
  159. $id = 4;
  160. break;
  161. case "MATERIAL":
  162. $id = 5;
  163. break;
  164. }
  165. return $id;
  166. }
  167. /**
  168. * Prints the help message.
  169. */
  170. function show_help(){
  171. echo "\nSwarfarm parser\n\n";
  172. echo "Refreshes data using the Swarfarm API.\n\n";
  173. echo "Usage:\n\n";
  174. echo " swarfarm_parser <options...>\n\n";
  175. echo "Options:\n\n";
  176. echo " +--------+------------------+---------------------------------------------------+\n";
  177. echo " | -s | --skip-downloads | Don't download images. |\n";
  178. echo " +--------+------------------+---------------------------------------------------+\n";
  179. echo " | -o | --only-downloads | Download images, but don't make changes to |\n";
  180. echo " | | | the database. |\n";
  181. echo " +--------+------------------+---------------------------------------------------+\n";
  182. echo " | -n | --only-new | Look for new units or skills, but don't update |\n";
  183. echo " | | | existing ones. |\n";
  184. echo " +--------+------------------+---------------------------------------------------+\n";
  185. echo " | -v [n] | --verbosity [n] | Controls the script output to the console. |\n";
  186. echo " | | | Values for [n]: |\n";
  187. echo " | | | 0: Only show critical errors. |\n";
  188. echo " | | | 1: Only error messages. |\n";
  189. echo " | | | 2: Only error and warning messages. |\n";
  190. echo " | | | 3: Standard output. |\n";
  191. echo " | | | 4: Include debug messages. |\n";
  192. echo " | | | 5: Print traces (lots of lines!). |\n";
  193. echo " +--------+------------------+---------------------------------------------------+\n";
  194. }
  195. /**
  196. * Establishes a connection with the database.
  197. *
  198. * @param string $name Archetype name (case insensitive).
  199. * @return resource Database connection
  200. */
  201. function connect_to_database(){
  202. // Connect to the database
  203. $db = new SQLite3(PATH . "application/sw.sqlite");
  204. if (!$db) {
  205. output(0, "Error connecting to th database: " . $db->lastErrorMsg());
  206. exit();
  207. }
  208. // Disable integrity
  209. $db->query("PRAGMA foreign_keys=OFF;");
  210. output(4, "Connected to databse: " . PATH . "application/sw.sqlite");
  211. return $db;
  212. }
  213. // Parse arguments
  214. $accepted = array(
  215. "--verbosity", "-v",
  216. "--skip-downloads", "-s",
  217. "--only-downloads", "-d",
  218. "--only-new", "-n",
  219. "--override-images", "-o",
  220. "--help", "-h"
  221. );
  222. for ($i = 1; $i < count($argv); $i++){
  223. if ($argv[$i] == "--help" || $argv[$i] == "-h"){
  224. show_help();
  225. return 0;
  226. }
  227. elseif (!in_array($argv[$i], $accepted)){
  228. echo "Unrecognized option " . $argv[$i] . "\n";
  229. return -1;
  230. }
  231. elseif ($argv[$i] == "--verbosity" || $argv[$i] == "-v"){
  232. if (count($argv) >= $i + 2 && is_int($argv[$i + 1]) && intval($argv[$i + 1]) >= 0 && intval($argv[$i + 1]) <= 5){
  233. $args["verbosity"] = intval($argv[$i + 1]);
  234. $i ++;
  235. }
  236. else{
  237. echo "Unrecognized value for parameter " . $argv[$i] . ": " . $argv[$i + 1] . "\n";
  238. echo "Accepted values are:\n";
  239. echo " 0 (critical)\n";
  240. echo " 1 (error)\n";
  241. echo " 2 (warning)\n";
  242. echo " 3 (info)\n";
  243. echo " 4 (debug)\n";
  244. echo " 5 (trace)\n";
  245. }
  246. }
  247. elseif ($argv[$i] == "--skip-downloads" || $argv[$i] == "-s"){
  248. if (in_array("-d", $argv)){
  249. echo "Conflicting arguments: '-d' and '" . $argv[$i] . "'\n";
  250. return -1;
  251. }
  252. elseif (in_array("--only-downloads", $argv)){
  253. echo "Conflicting arguments: '--only-downloads' and '" . $argv[$i] . "'\n";
  254. return -1;
  255. }
  256. else{
  257. $args["skip_downloads"] = true;
  258. }
  259. }
  260. elseif ($argv[$i] == "--only-downloads" || $argv[$i] == "-s"){
  261. if (in_array("-s", $argv)){
  262. echo "Conflicting arguments: '-s' and '" . $argv[$i] . "'\n";
  263. return -1;
  264. }
  265. elseif (in_array("--skip-downloads", $argv)){
  266. echo "Conflicting arguments: '--skip-downloads' and '" . $argv[$i] . "'\n";
  267. return -1;
  268. }
  269. else{
  270. $args["only_downloads"] = true;
  271. }
  272. }
  273. elseif ($argv[$i] == "--only-new" || $argv[$i] == "-n"){
  274. $args["only_new"] = true;
  275. }
  276. elseif ($argv[$i] == "--override-images" || $argv[$i] == "-o"){
  277. if (in_array("-s", $argv)){
  278. echo "Conflicting arguments: '-s' and '" . $argv[$i] . "'\n";
  279. return -1;
  280. }
  281. elseif (in_array("--skip-downloads", $argv)){
  282. echo "Conflicting arguments: '--skip-downloads' and '" . $argv[$i] . "'\n";
  283. return -1;
  284. }
  285. else{
  286. $args["override_images"] = true;
  287. }
  288. }
  289. }
  290. output(4, "Resolved arguments:");
  291. foreach($args as $key => $value) {
  292. output(4, " $key => " . var_export($value, true));
  293. }
  294. // Connect to the database
  295. $db = connect_to_database();
  296. // Loop skills pages
  297. $next = URL_SKILL;
  298. while ($next != null){
  299. output(3, "Reading skills page: $next");
  300. $contents = file_get_contents($next);
  301. if ($contents === false){
  302. output(0, "Unable to read skill page: $next");
  303. return -1;
  304. }
  305. $contents = json_decode($contents);
  306. $next = $contents->next;
  307. $list = $contents->results;
  308. foreach ($list as $skill){
  309. $statement = $db->prepare("SELECT * FROM k_skill WHERE id = :id");
  310. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  311. $q = $statement->execute();
  312. $r = $q->fetchArray(SQLITE3_ASSOC);
  313. if (!$r){
  314. // New skill, insert directly
  315. $statement = $db->prepare("
  316. INSERT INTO k_skill(
  317. id,
  318. name,
  319. description,
  320. slot,
  321. cooltime,
  322. hits,
  323. passive,
  324. aoe,
  325. max_level,
  326. multiplier_formula
  327. ) VALUES (
  328. :id,
  329. :name,
  330. :description,
  331. :slot,
  332. :cooltime,
  333. :hits,
  334. :passive,
  335. :aoe,
  336. :max_level,
  337. :multiplier_formula
  338. );
  339. ");
  340. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  341. $statement->bindValue(":name", $skill->name, SQLITE3_TEXT);
  342. $statement->bindValue(":description", $skill->name, SQLITE3_TEXT);
  343. $statement->bindValue(":slot", $skill->slot, SQLITE3_TEXT);
  344. $statement->bindValue(":cooltime", $skill->cooltime, SQLITE3_INTEGER);
  345. $statement->bindValue(":hits", $skill->hits, SQLITE3_INTEGER);
  346. $statement->bindValue(":passive", $skill->passive, SQLITE3_INTEGER);
  347. $statement->bindValue(":aoe", $skill->aoe, SQLITE3_INTEGER);
  348. $statement->bindValue(":max_level", $skill->max_level, SQLITE3_INTEGER);
  349. $statement->bindValue(":multiplier_formula", $skill->multiplier_formula, SQLITE3_TEXT);
  350. output(4, "QUERY: " . $statement->getSQL(true));
  351. $statement->execute();
  352. $url = 'https://swarfarm.com/static/herders/images/skills/' . $skill->icon_filename;
  353. $out = PATH . "public/img/skill/" . sprintf('%08d', $skill->com2us_id) . ".png";
  354. download($url, $out);
  355. $level = 1;
  356. $statement = $db->prepare("INSERT INTO k_skill_level (skill, level, description) VALUES (:skill, :level, :description);");
  357. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  358. $statement->bindValue(":level", $level, SQLITE3_INTEGER);
  359. foreach ($skill->upgrades as $upgrade){
  360. $level ++;
  361. $statement = $db->prepare("INSERT INTO k_skill_level (skill, level, description) VALUES (:skill, :level, :description);");
  362. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  363. $statement->bindValue(":level", $level, SQLITE3_INTEGER);
  364. $statement->bindValue(":description", str_replace("{0}", $upgrade->amount, $upgrade->effect), SQLITE3_TEXT);
  365. output(4, "QUERY: " . $statement->getSQL(true));
  366. $statement->execute();
  367. }
  368. foreach ($skill->effects as $effect){
  369. $statement = $db->prepare("INSERT INTO k_skill_effect (skill, effect) VALUES (:skill, :effect);");
  370. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  371. $statement->bindValue(":effect", $effect->effect->id, SQLITE3_INTEGER);
  372. output(4, "QUERY: " . $statement->getSQL(true));
  373. $statement->execute();
  374. }
  375. }
  376. else{
  377. // Existing skill, compare all values
  378. if ($r["name"] != $skill->name){
  379. $statement = $db->prepare("UPDATE k_skill SET name = :name WHERE id = :id;");
  380. $statement->bindValue(":name", $skill->name, SQLITE3_TEXT);
  381. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  382. output(4, "QUERY: " . $statement->getSQL(true));
  383. $statement->execute();
  384. }
  385. if ($r["description"] != $skill->description){
  386. $statement = $db->prepare("UPDATE k_skill SET description = :description WHERE id = :id;");
  387. $statement->bindValue(":description", $skill->description, SQLITE3_TEXT);
  388. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  389. output(4, "QUERY: " . $statement->getSQL(true));
  390. $statement->execute();
  391. }
  392. if ($r["slot"] != $skill->slot){
  393. $statement = $db->prepare("UPDATE k_skill SET slot = :slot WHERE id = :id;");
  394. $statement->bindValue(":slot", $skill->slot, SQLITE3_TEXT);
  395. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  396. output(4, "QUERY: " . $statement->getSQL(true));
  397. $statement->execute();
  398. }
  399. if ($r["cooltime"] != $skill->cooltime){
  400. $statement = $db->prepare("UPDATE k_skill SET cooltime = :cooltime WHERE id = :id;");
  401. $statement->bindValue(":cooltime", $skill->cooltime, SQLITE3_TEXT);
  402. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  403. output(4, "QUERY: " . $statement->getSQL(true));
  404. $statement->execute();
  405. }
  406. if ($r["hits"] != $skill->hits){
  407. $statement = $db->prepare("UPDATE k_skill SET hits = :hits WHERE id = :id;");
  408. $statement->bindValue(":hits", $skill->hits, SQLITE3_TEXT);
  409. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  410. output(4, "QUERY: " . $statement->getSQL(true));
  411. $statement->execute();
  412. }
  413. $passive = ($skill->passive == 1) ? (1) : (0);
  414. if ($r["passive"] != $passive){
  415. $statement = $db->prepare("UPDATE k_skill SET passive = :passive WHERE id = :id;");
  416. $statement->bindValue(":passive", $passive, SQLITE3_TEXT);
  417. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  418. output(4, "QUERY: " . $statement->getSQL(true));
  419. $statement->execute();
  420. }
  421. $aoe = ($skill->aoe == 1) ? (1) : (0);
  422. if ($r["aoe"] != $aoe){
  423. $statement = $db->prepare("UPDATE k_skill SET aoe = :aoe WHERE id = :id;");
  424. $statement->bindValue(":aoe", $aoe, SQLITE3_TEXT);
  425. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  426. output(4, "QUERY: " . $statement->getSQL(true));
  427. $statement->execute();
  428. }
  429. if ($r["max_level"] != $skill->max_level){
  430. $statement = $db->prepare("UPDATE k_skill SET max_level = :max_level WHERE id = :id;");
  431. $statement->bindValue(":max_level", $skill->max_level, SQLITE3_TEXT);
  432. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  433. output(4, "QUERY: " . $statement->getSQL(true));
  434. $statement->execute();
  435. }
  436. if ($r["multiplier_formula"] != $skill->multiplier_formula){
  437. $statement = $db->prepare("UPDATE k_skill SET multiplier_formula = :multiplier_formula WHERE id = :id;");
  438. $statement->bindValue(":multiplier_formula", $skill->multiplier_formula, SQLITE3_TEXT);
  439. $statement->bindValue(":id", $skill->com2us_id, SQLITE3_INTEGER);
  440. output(4, "QUERY: " . $statement->getSQL(true));
  441. $statement->execute();
  442. }
  443. // Compare existing effects
  444. $statement = $db->prepare("SELECT count(effect) AS c FROM k_skill_effect WHERE skill = :skill;");
  445. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  446. $q = $statement->execute();
  447. $r = $q->fetchArray(SQLITE3_ASSOC);
  448. if ($r["c"] != sizeof($skill->effects)){
  449. $statement = $db->prepare("DELETE FROM k_skill_effect WHERE skill = :skill;");
  450. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  451. output(4, "QUERY: " . $statement->getSQL(true));
  452. $statement->execute();
  453. foreach ($skill->effects as $effect){
  454. $statement = $db->prepare("INSERT INTO k_skill_effect (skill, effect) VALUES (:skill, :effect);");
  455. $statement->bindValue(":skill", $skill->com2us_id, SQLITE3_INTEGER);
  456. $statement->bindValue(":effect", $effect->effect->id, SQLITE3_INTEGER);
  457. output(4, "QUERY: " . $statement->getSQL(true));
  458. $statement->execute();
  459. }
  460. }
  461. // Image download
  462. $out = PATH . "public/img/skill/" . sprintf('%08d', $skill->com2us_id) . ".png";
  463. $url = 'https://swarfarm.com/static/herders/images/skills/' . $skill->icon_filename;
  464. download($url, $out);
  465. }
  466. }
  467. //echo "NEXTPAGE: " . $next;
  468. }
  469. // Loop units pages
  470. $next = URL_UNIT;
  471. while ($next != null){
  472. output(3, "Reading units page: $next");
  473. $contents = file_get_contents($next);
  474. if($contents === false){
  475. output(0, "Unable to retrieve monster list.");
  476. return -1;
  477. }
  478. $contents = json_decode($contents);
  479. $next = $contents->next;
  480. $list = $contents->results;
  481. foreach ($list as $unit){
  482. $statement = $db->prepare("SELECT * FROM k_unit WHERE id = :id");
  483. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  484. $q = $statement->execute();
  485. $r = $q->fetchArray(SQLITE3_ASSOC);
  486. if (!$r){
  487. $statement = $db->prepare("
  488. INSERT INTO k_unit(
  489. id,
  490. family,
  491. name,
  492. element,
  493. archetype,
  494. base_stars,
  495. natural_stars,
  496. obtainable,
  497. can_awaken,
  498. awaken_bonus,
  499. skill_ups_to_max,
  500. leader_skill,
  501. hp,
  502. attack,
  503. defense,
  504. speed,
  505. crit_rate,
  506. crit_damage,
  507. resistance,
  508. accuracy,
  509. raw_hp,
  510. raw_attack,
  511. raw_defense,
  512. max_lvl_hp,
  513. max_lvl_attack,
  514. max_lvl_defense,
  515. awakens_from,
  516. awakens_to,
  517. fusion_food,
  518. homunculus,
  519. craft_cost
  520. ) VALUES (
  521. :id,
  522. :family,
  523. :name,
  524. :element,
  525. :archetype,
  526. :base_stars,
  527. :natural_stars,
  528. :obtainable,
  529. :can_awaken,
  530. :awaken_bonus,
  531. :skill_ups_to_max,
  532. :leader_skill,
  533. :hp,
  534. :attack,
  535. :defense,
  536. :speed,
  537. :crit_rate,
  538. :crit_damage,
  539. :resistance,
  540. :accuracy,
  541. :raw_hp,
  542. :raw_attack,
  543. :raw_defense,
  544. :max_lvl_hp,
  545. :max_lvl_attack,
  546. :max_lvl_defense,
  547. :awakens_from,
  548. :awakens_to,
  549. :fusion_food,
  550. :homunculus,
  551. :craft_cost
  552. );
  553. ");
  554. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_TEXT);
  555. $statement->bindValue(":family", $unit->family_id, SQLITE3_INTEGER);
  556. $statement->bindValue(":name", $unit->name, SQLITE3_TEXT);
  557. $statement->bindValue(":element", get_element_id($unit->element), SQLITE3_INTEGER);
  558. $statement->bindValue(":archetype", get_archetype_id($unit->archetype), SQLITE3_INTEGER);
  559. $statement->bindValue(":base_stars", $unit->base_stars, SQLITE3_INTEGER);
  560. $statement->bindValue(":natural_stars", $unit->natural_stars, SQLITE3_INTEGER);
  561. $statement->bindValue(":obtainable", $unit->obtainable, SQLITE3_INTEGER);
  562. $statement->bindValue(":can_awaken", $unit->can_awaken, SQLITE3_INTEGER);
  563. $statement->bindValue(":awaken_bonus", $unit->awaken_bonus, SQLITE3_TEXT);
  564. $statement->bindValue(":skill_ups_to_max", $unit->skill_ups_to_max, SQLITE3_INTEGER);
  565. if (isset($unit->leader_skill->id)){
  566. $statement->bindValue(":leader_skill", $unit->leader_skill, SQLITE3_INTEGER);
  567. }
  568. else{
  569. $statement->bindValue(":leader_skill", null, SQLITE3_INTEGER);
  570. }
  571. $statement->bindValue(":hp", $unit->base_hp, SQLITE3_INTEGER);
  572. $statement->bindValue(":attack", $unit->base_attack, SQLITE3_INTEGER);
  573. $statement->bindValue(":defense", $unit->base_defense, SQLITE3_INTEGER);
  574. $statement->bindValue(":speed", $unit->speed, SQLITE3_INTEGER);
  575. $statement->bindValue(":crit_rate", $unit->crit_rate, SQLITE3_INTEGER);
  576. $statement->bindValue(":crit_damage", $unit->crit_damage, SQLITE3_INTEGER);
  577. $statement->bindValue(":resistance", $unit->resistance, SQLITE3_INTEGER);
  578. $statement->bindValue(":accuracy", $unit->accuracy, SQLITE3_INTEGER);
  579. $statement->bindValue(":raw_hp", $unit->raw_hp, SQLITE3_INTEGER);
  580. $statement->bindValue(":raw_attack", $unit->raw_attack, SQLITE3_INTEGER);
  581. $statement->bindValue(":raw_defense", $unit->raw_defense, SQLITE3_INTEGER);
  582. $statement->bindValue(":max_lvl_hp", $unit->max_lvl_hp, SQLITE3_INTEGER);
  583. $statement->bindValue(":max_lvl_attack", $unit->max_lvl_attack, SQLITE3_INTEGER);
  584. $statement->bindValue(":max_lvl_defense", $unit->max_lvl_defense, SQLITE3_INTEGER);
  585. $statement->bindValue(":awakens_from", get_com2us_id($unit->awakens_from), SQLITE3_TEXT);
  586. $statement->bindValue(":awakens_to", get_com2us_id($unit->awakens_to), SQLITE3_TEXT);
  587. $statement->bindValue(":fusion_food", $unit->fusion_food, SQLITE3_INTEGER);
  588. $statement->bindValue(":homunculus", $unit->homunculus, SQLITE3_INTEGER);
  589. $statement->bindValue(":craft_cost", 0, SQLITE3_INTEGER);
  590. output(4, "QUERY: " . $statement->getSQL(true));
  591. $statement->execute();
  592. $url = 'https://swarfarm.com/static/herders/images/monsters/' . $unit->image_filename;
  593. $out = PATH . "public/img/unit/" . sprintf('%08d', $unit->com2us_id) . ".png";
  594. download($url, $out);
  595. // Skills (not in database yet, but they will be once skills are parsed)
  596. foreach ($unit->skills as $skill){
  597. $statement = $db->prepare("INSERT INTO k_unit_skill (unit, skill) VALUES (:unit, :skill);");
  598. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  599. $statement->bindValue(":skill", $skill, SQLITE3_INTEGER);
  600. output(4, "QUERY: " . $statement->getSQL(true));
  601. $statement->execute();
  602. }
  603. // Essences to awaken
  604. foreach ($unit->awaken_cost as $essence){
  605. $statement = $db->prepare("INSERT INTO k_unit_essence (unit, item, amount) VALUES (:unit, :item, :amount);");
  606. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  607. $statement->bindValue(":item", $essence->item->com2us_id, SQLITE3_INTEGER);
  608. $statement->bindValue(":amount", $essence->quantity, SQLITE3_INTEGER);
  609. output(4, "QUERY: " . $statement->getSQL(true));
  610. $statement->execute();
  611. }
  612. // Unit sources
  613. foreach ($unit->source as $source){
  614. $statement = $db->prepare("INSERT INTO k_unit_source (unit, source) VALUES (:unit, :source);");
  615. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  616. $statement->bindValue(":source", $source->id, SQLITE3_INTEGER);
  617. output(4, "QUERY: " . $statement->getSQL(true));
  618. $statement->execute();
  619. }
  620. }
  621. else{
  622. // Compare all values
  623. if ($r["family"] != $unit->family_id){
  624. $statement = $db->prepare("UPDATE k_unit SET family = :family WHERE id = :id;");
  625. $statement->bindValue(":family", $unit->family_id, SQLITE3_INTEGER);
  626. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  627. output(4, "QUERY: " . $statement->getSQL(true));
  628. $statement->execute();
  629. }
  630. if ($r["name"] != $unit->name){
  631. $statement = $db->prepare("UPDATE k_unit SET name = :name WHERE id = :id;");
  632. $statement->bindValue(":name", $unit->name, SQLITE3_TEXT);
  633. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  634. output(4, "QUERY: " . $statement->getSQL(true));
  635. $statement->execute();
  636. }
  637. $element = get_element_id($unit->element);
  638. if ($r["element"] != $element){
  639. $statement = $db->prepare("UPDATE k_unit SET element = :element WHERE id = :id;");
  640. $statement->bindValue(":element", $element, SQLITE3_TEXT);
  641. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  642. output(4, "QUERY: " . $statement->getSQL(true));
  643. $statement->execute();
  644. }
  645. $archetype = get_archetype_id($unit->archetype);
  646. if ($r["archetype"] != $archetype){
  647. $statement = $db->prepare("UPDATE k_unit SET archetype = :archetype WHERE id = :id;");
  648. $statement->bindValue(":archetype", $archetype, SQLITE3_TEXT);
  649. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  650. output(4, "QUERY: " . $statement->getSQL(true));
  651. $statement->execute();
  652. }
  653. if ($r["base_stars"] != $unit->base_stars){
  654. $statement = $db->prepare("UPDATE k_unit SET base_stars = :base_stars WHERE id = :id;");
  655. $statement->bindValue(":base_stars", $unit->base_stars, SQLITE3_INTEGER);
  656. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  657. output(4, "QUERY: " . $statement->getSQL(true));
  658. $statement->execute();
  659. }
  660. if ($r["natural_stars"] != $unit->natural_stars){
  661. $statement = $db->prepare("UPDATE k_unit SET natural_stars = :natural_stars WHERE id = :id;");
  662. $statement->bindValue(":natural_stars", $unit->natural_stars, SQLITE3_INTEGER);
  663. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  664. output(4, "QUERY: " . $statement->getSQL(true));
  665. $statement->execute();
  666. }
  667. if ($r["obtainable"] != $unit->obtainable){
  668. $statement = $db->prepare("UPDATE k_unit SET obtainable = :obtainable WHERE id = :id;");
  669. $statement->bindValue(":obtainable", $unit->obtainable, SQLITE3_INTEGER);
  670. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  671. output(4, "QUERY: " . $statement->getSQL(true));
  672. $statement->execute();
  673. }
  674. if ($r["can_awaken"] != $unit->can_awaken){
  675. $statement = $db->prepare("UPDATE k_unit SET can_awaken = :can_awaken WHERE id = :id;");
  676. $statement->bindValue(":can_awaken", $unit->can_awaken, SQLITE3_INTEGER);
  677. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  678. output(4, "QUERY: " . $statement->getSQL(true));
  679. $statement->execute();
  680. }
  681. if ($r["awaken_bonus"] != $unit->awaken_bonus && $unit->awaken_bonus != 0){
  682. $statement = $db->prepare("UPDATE k_unit SET awaken_bonus = :awaken_bonus WHERE id = :id;");
  683. $statement->bindValue(":awaken_bonus", $unit->awaken_bonus, SQLITE3_TEXT);
  684. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_TEXT);
  685. output(4, "QUERY: " . $statement->getSQL(true));
  686. $statement->execute();
  687. }
  688. if ($r["skill_ups_to_max"] != $unit->skill_ups_to_max){
  689. $statement = $db->prepare("UPDATE k_unit SET skill_ups_to_max = :skill_ups_to_max WHERE id = :id;");
  690. $statement->bindValue(":skill_ups_to_max", $unit->skill_ups_to_max, SQLITE3_INTEGER);
  691. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  692. output(4, "QUERY: " . $statement->getSQL(true));
  693. $statement->execute();
  694. }
  695. if (isset($unit->leader_skill->id) && $r["leader_skill"] != $unit->leader_skill->id){
  696. $statement = $db->prepare("UPDATE k_unit SET leader_skill = :leader_skill WHERE id = :id;");
  697. $statement->bindValue(":leader_skill", $unit->leader_skill->id, SQLITE3_TEXT);
  698. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  699. output(4, "QUERY: " . $statement->getSQL(true));
  700. $statement->execute();
  701. }
  702. if ($r["hp"] != $unit->base_hp){
  703. $statement = $db->prepare("UPDATE k_unit SET hp = :hp WHERE id = :id;");
  704. $statement->bindValue(":hp", $unit->base_hp, SQLITE3_INTEGER);
  705. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  706. output(4, "QUERY: " . $statement->getSQL(true));
  707. $statement->execute();
  708. }
  709. if ($r["attack"] != $unit->base_attack){
  710. $statement = $db->prepare("UPDATE k_unit SET attack = :attack WHERE id = :id;");
  711. $statement->bindValue(":attack", $unit->base_attack, SQLITE3_INTEGER);
  712. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  713. output(4, "QUERY: " . $statement->getSQL(true));
  714. $statement->execute();
  715. }
  716. if ($r["defense"] != $unit->base_defense){
  717. $statement = $db->prepare("UPDATE k_unit SET defense = :defense WHERE id = :id;");
  718. $statement->bindValue(":defense", $unit->base_defense, SQLITE3_INTEGER);
  719. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  720. output(4, "QUERY: " . $statement->getSQL(true));
  721. $statement->execute();
  722. }
  723. if ($r["speed"] != $unit->speed){
  724. $statement = $db->prepare("UPDATE k_unit SET speed = :speed WHERE id = :id;");
  725. $statement->bindValue(":speed", $unit->speed, SQLITE3_INTEGER);
  726. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  727. output(4, "QUERY: " . $statement->getSQL(true));
  728. $statement->execute();
  729. }
  730. if ($r["crit_rate"] != $unit->crit_rate){
  731. $statement = $db->prepare("UPDATE k_unit SET crit_rate = :crit_rate WHERE id = :id;");
  732. $statement->bindValue(":crit_rate", $unit->crit_rate, SQLITE3_INTEGER);
  733. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  734. output(4, "QUERY: " . $statement->getSQL(true));
  735. $statement->execute();
  736. }
  737. if ($r["crit_damage"] != $unit->crit_damage){
  738. $statement = $db->prepare("UPDATE k_unit SET crit_damage = :crit_damage WHERE id = :id;");
  739. $statement->bindValue(":crit_damage", $unit->crit_damage, SQLITE3_INTEGER);
  740. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  741. output(4, "QUERY: " . $statement->getSQL(true));
  742. $statement->execute();
  743. }
  744. if ($r["resistance"] != $unit->resistance){
  745. $statement = $db->prepare("UPDATE k_unit SET resistance = :resistance WHERE id = :id;");
  746. $statement->bindValue(":resistance", $unit->resistance, SQLITE3_INTEGER);
  747. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  748. output(4, "QUERY: " . $statement->getSQL(true));
  749. $statement->execute();
  750. }
  751. if ($r["accuracy"] != $unit->accuracy){
  752. $statement = $db->prepare("UPDATE k_unit SET accuracy = :accuracy WHERE id = :id;");
  753. $statement->bindValue(":accuracy", $unit->accuracy, SQLITE3_INTEGER);
  754. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  755. output(4, "QUERY: " . $statement->getSQL(true));
  756. $statement->execute();
  757. }
  758. if ($r["raw_hp"] != $unit->raw_hp){
  759. $statement = $db->prepare("UPDATE k_unit SET raw_hp = :raw_hp WHERE id = :id;");
  760. $statement->bindValue(":raw_hp", $unit->raw_hp, SQLITE3_INTEGER);
  761. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  762. output(4, "QUERY: " . $statement->getSQL(true));
  763. $statement->execute();
  764. }
  765. if ($r["raw_attack"] != $unit->raw_attack){
  766. $statement = $db->prepare("UPDATE k_unit SET raw_attack = :raw_attack WHERE id = :id;");
  767. $statement->bindValue(":raw_attack", $unit->raw_attack, SQLITE3_INTEGER);
  768. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  769. output(4, "QUERY: " . $statement->getSQL(true));
  770. $statement->execute();
  771. }
  772. if ($r["raw_defense"] != $unit->raw_defense){
  773. $statement = $db->prepare("UPDATE k_unit SET raw_defense = :raw_defense WHERE id = :id;");
  774. $statement->bindValue(":raw_defense", $unit->raw_defense, SQLITE3_INTEGER);
  775. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  776. output(4, "QUERY: " . $statement->getSQL(true));
  777. $statement->execute();
  778. }
  779. if ($r["max_lvl_hp"] != $unit->max_lvl_hp){
  780. $statement = $db->prepare("UPDATE k_unit SET max_lvl_hp = :max_lvl_hp WHERE id = :id;");
  781. $statement->bindValue(":max_lvl_hp", $unit->max_lvl_hp, SQLITE3_INTEGER);
  782. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  783. output(4, "QUERY: " . $statement->getSQL(true));
  784. $statement->execute();
  785. }
  786. if ($r["max_lvl_attack"] != $unit->max_lvl_attack){
  787. $statement = $db->prepare("UPDATE k_unit SET max_lvl_attack = :max_lvl_attack WHERE id = :id;");
  788. $statement->bindValue(":max_lvl_attack", $unit->max_lvl_attack, SQLITE3_INTEGER);
  789. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  790. output(4, "QUERY: " . $statement->getSQL(true));
  791. $statement->execute();
  792. }
  793. if ($r["max_lvl_defense"] != $unit->max_lvl_defense){
  794. $statement = $db->prepare("UPDATE k_unit SET max_lvl_defense = :max_lvl_defense WHERE id = :id;");
  795. $statement->bindValue(":max_lvl_defense", $unit->max_lvl_defense, SQLITE3_INTEGER);
  796. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  797. output(4, "QUERY: " . $statement->getSQL(true));
  798. $statement->execute();
  799. }
  800. $com2us_id = get_com2us_id($unit->awakens_from);
  801. if ($r["awakens_from"] != $com2us_id){
  802. $statement = $db->prepare("UPDATE k_unit SET awakens_from = :awakens_from WHERE id = :id;");
  803. $statement->bindValue(":awakens_from", $com2us_id, SQLITE3_INTEGER);
  804. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  805. output(4, "QUERY: " . $statement->getSQL(true));
  806. $statement->execute();
  807. }
  808. $com2us_id = get_com2us_id($unit->awakens_to);
  809. if ($r["awakens_to"] != $com2us_id){
  810. $statement = $db->prepare("UPDATE k_unit SET awakens_to = :awakens_to WHERE id = :id;");
  811. $statement->bindValue(":awakens_to", $com2us_id, SQLITE3_INTEGER);
  812. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  813. output(4, "QUERY: " . $statement->getSQL(true));
  814. $statement->execute();
  815. }
  816. if ($r["fusion_food"] != $unit->fusion_food){
  817. $statement = $db->prepare("UPDATE k_unit SET fusion_food = :fusion_food WHERE id = :id;");
  818. $statement->bindValue(":fusion_food", $unit->fusion_food, SQLITE3_INTEGER);
  819. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  820. output(4, "QUERY: " . $statement->getSQL(true));
  821. $statement->execute();
  822. }
  823. if ($r["homunculus"] != $unit->homunculus){
  824. $statement = $db->prepare("UPDATE k_unit SET homunculus = :homunculus WHERE id = :id;");
  825. $statement->bindValue(":homunculus", $unit->homunculus, SQLITE3_INTEGER);
  826. $statement->bindValue(":id", $unit->com2us_id, SQLITE3_INTEGER);
  827. output(4, "QUERY: " . $statement->getSQL(true));
  828. $statement->execute();
  829. }
  830. // Loop skills. Only for inserting in k_skill and k_unit_skill
  831. $statement = $db->prepare("SELECT count(skill) AS c FROM k_unit_skill WHERE unit = :unit;");
  832. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  833. $q = $statement->execute();
  834. $r = $q->fetchArray(SQLITE3_ASSOC);
  835. if ($r["c"] != sizeof($unit->skills)){
  836. $statement = $db->prepare("DELETE FROM k_unit_skill WHERE unit = :unit;");
  837. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  838. output(4, "QUERY: " . $statement->getSQL(true));
  839. $statement->execute();
  840. foreach ($unit->skills as $skill){
  841. $statement = $db->prepare("INSERT INTO k_unit_skill (unit, skill) VALUES (:unit, :skill);");
  842. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  843. $statement->bindValue(":skill", $skill, SQLITE3_INTEGER);
  844. output(4, "QUERY: " . $statement->getSQL(true));
  845. $statement->execute();
  846. }
  847. }
  848. // Essences to awaken
  849. $statement = $db->prepare("SELECT count(item) AS c FROM k_unit_essence WHERE unit = :unit;");
  850. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  851. $q = $statement->execute();
  852. $r = $q->fetchArray(SQLITE3_ASSOC);
  853. if ($r["c"] != sizeof($unit->awaken_cost)){
  854. $statement = $db->prepare("DELETE FROM k_unit_essence WHERE unit = :unit;");
  855. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  856. output(4, "QUERY: " . $statement->getSQL(true));
  857. $statement->execute();
  858. foreach ($unit->awaken_cost as $essence){
  859. $statement = $db->prepare("INSERT INTO k_unit_essence (unit, item, amount) VALUES (:unit, :item, :amount);");
  860. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  861. $statement->bindValue(":item", $essence->item->com2us_id, SQLITE3_INTEGER);
  862. $statement->bindValue(":amount", $essence->quantity, SQLITE3_INTEGER);
  863. output(4, "QUERY: " . $statement->getSQL(true));
  864. $statement->execute();
  865. }
  866. }
  867. // Unit sources
  868. $statement = $db->prepare("SELECT count(source) AS c FROM k_unit_source WHERE unit = :unit;");
  869. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  870. $q = $statement->execute();
  871. $r = $q->fetchArray(SQLITE3_ASSOC);
  872. if ($r["c"] != sizeof($unit->source)){
  873. $statement = $db->prepare("DELETE FROM k_unit_source WHERE unit = :unit;");
  874. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  875. output(4, "QUERY: " . $statement->getSQL(true));
  876. $statement->execute();
  877. foreach ($unit->source as $source){
  878. $statement = $db->prepare("INSERT INTO k_unit_source (unit, source) VALUES (:unit, :source);");
  879. $statement->bindValue(":unit", $unit->com2us_id, SQLITE3_INTEGER);
  880. $statement->bindValue(":source", $source->id, SQLITE3_INTEGER);
  881. output(4, "QUERY: " . $statement->getSQL(true));
  882. $statement->execute();
  883. }
  884. }
  885. // Image download
  886. $out = PATH . "public/img/unit/" . sprintf('%08d', $unit->com2us_id) . ".png";
  887. $url = 'https://swarfarm.com/static/herders/images/monsters/' . $unit->image_filename;
  888. download($url, $out);
  889. }
  890. }
  891. //echo "NEXTPAGE: " . $next;
  892. }