use xmlrpc to load pets, not json.php

The AMFPHP gateway's json.php endpoint has always had a problem parsing pets whose names start with digits… I've dug into it before, and checked again today, and there really is just no way around it: d584b58e95/core/json/app/Actions.php (L43)

And there aren't any reliable AMFPHP Node libraries out there to make the actual native AMF call.

Buuuut! In today's investigation, I noticed the xmlrpc.php endpoint for the first time. And, wouldn't you know it, there's //great// reliability for something as enterprise-standard as that!

So here, I've switched over to using an xmlrpc client library, which simplifies our calling code //and// makes number pets work correctly 😁 I wouldn't have done it just for the simplification, I think bringing in a library is net more complexity… but getting this finally right is a big relief.
This commit is contained in:
Emi Matchu 2020-10-22 23:22:04 -07:00
parent 57889a3a88
commit e7cc20876b
3 changed files with 34 additions and 30 deletions

View file

@ -35,7 +35,8 @@
"react-icons": "^3.11.0", "react-icons": "^3.11.0",
"react-router-dom": "^5.1.2", "react-router-dom": "^5.1.2",
"react-scripts": "3.4.1", "react-scripts": "3.4.1",
"react-transition-group": "^4.3.0" "react-transition-group": "^4.3.0",
"xmlrpc": "^1.3.2"
}, },
"scripts": { "scripts": {
"start": "yarn build-cached-data && react-app-rewired start", "start": "yarn build-cached-data && react-app-rewired start",

View file

@ -1,5 +1,8 @@
const util = require("util");
const fetch = require("node-fetch"); const fetch = require("node-fetch");
const { gql } = require("apollo-server"); const { gql } = require("apollo-server");
const xmlrpc = require("xmlrpc");
const { getPoseFromPetState } = require("../util"); const { getPoseFromPetState } = require("../util");
const { saveModelingData } = require("../modeling"); const { saveModelingData } = require("../modeling");
@ -87,38 +90,25 @@ const resolvers = {
}, },
}; };
async function loadPetMetaData(petName) { const neopetsXmlrpcClient = xmlrpc.createClient({
const url = `http://www.neopets.com/amfphp/json.php/PetService.getPet/${petName}`; host: "www.neopets.com",
const res = await fetch(url); port: 80,
if (!res.ok) { path: "/amfphp/xmlrpc.php",
throw new Error( });
`for pet meta data, neopets.com returned: ` + const neopetsXmlrpcCall = util
`${res.status} ${res.statusText}. (${url})` .promisify(neopetsXmlrpcClient.methodCall)
); .bind(neopetsXmlrpcClient);
}
const json = await res.json(); async function loadPetMetaData(petName) {
return json; const response = await neopetsXmlrpcCall("PetService.getPet", [petName]);
return response;
} }
async function loadCustomPetData(petName) { async function loadCustomPetData(petName) {
const url = const response = await neopetsXmlrpcCall("CustomPetService.getViewerData", [
`http://www.neopets.com/amfphp/json.php/CustomPetService.getViewerData` + petName,
`/${petName}`; ]);
const res = await fetch(url); return response;
if (!res.ok) {
throw new Error(
`for custom pet data, neopets.com returned: ` +
`${res.status} ${res.statusText}. (${url})`
);
}
const json = await res.json();
if (!json.custom_pet) {
throw new Error(`missing custom_pet data`);
}
return json;
} }
function getPoseFromPetData(petMetaData, petCustomData) { function getPoseFromPetData(petMetaData, petCustomData) {

View file

@ -16011,7 +16011,7 @@ sax@1.2.1:
resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.1.tgz#7b8e656190b228e81a66aea748480d828cd2d37a" resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.1.tgz#7b8e656190b228e81a66aea748480d828cd2d37a"
integrity sha1-e45lYZCyKOgaZq6nSEgNgozS03o= integrity sha1-e45lYZCyKOgaZq6nSEgNgozS03o=
sax@>=0.6.0, sax@^1.2.4, sax@~1.2.4: sax@1.2.x, sax@>=0.6.0, sax@^1.2.4, sax@~1.2.4:
version "1.2.4" version "1.2.4"
resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.4.tgz#2816234e2378bddc4e5354fab5caa895df7100d9" resolved "https://registry.yarnpkg.com/sax/-/sax-1.2.4.tgz#2816234e2378bddc4e5354fab5caa895df7100d9"
integrity sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw== integrity sha512-NqVDv9TpANUjFm0N8uM5GxL36UgKi9/atZw+x7YFnQ8ckwFGKrl4xX4yWtrey3UJm5nP1kUbnYgLopqWNSRhWw==
@ -18440,6 +18440,11 @@ xml2js@^0.4.5:
sax ">=0.6.0" sax ">=0.6.0"
xmlbuilder "~11.0.0" xmlbuilder "~11.0.0"
xmlbuilder@8.2.x:
version "8.2.2"
resolved "https://registry.yarnpkg.com/xmlbuilder/-/xmlbuilder-8.2.2.tgz#69248673410b4ba42e1a6136551d2922335aa773"
integrity sha1-aSSGc0ELS6QuGmE2VR0pIjNap3M=
xmlbuilder@~11.0.0: xmlbuilder@~11.0.0:
version "11.0.1" version "11.0.1"
resolved "https://registry.yarnpkg.com/xmlbuilder/-/xmlbuilder-11.0.1.tgz#be9bae1c8a046e76b31127726347d0ad7002beb3" resolved "https://registry.yarnpkg.com/xmlbuilder/-/xmlbuilder-11.0.1.tgz#be9bae1c8a046e76b31127726347d0ad7002beb3"
@ -18455,6 +18460,14 @@ xmlchars@^2.1.1:
resolved "https://registry.yarnpkg.com/xmlchars/-/xmlchars-2.2.0.tgz#060fe1bcb7f9c76fe2a17db86a9bc3ab894210cb" resolved "https://registry.yarnpkg.com/xmlchars/-/xmlchars-2.2.0.tgz#060fe1bcb7f9c76fe2a17db86a9bc3ab894210cb"
integrity sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw== integrity sha512-JZnDKK8B0RCDw84FNdDAIpZK+JuJw+s7Lz8nksI7SIuU3UXJJslUthsi+uWBUYOwPFwW7W7PRLRfUKpxjtjFCw==
xmlrpc@^1.3.2:
version "1.3.2"
resolved "https://registry.yarnpkg.com/xmlrpc/-/xmlrpc-1.3.2.tgz#26b2ea347848d028aac7e7514b5351976de3e83d"
integrity sha1-JrLqNHhI0Ciqx+dRS1NRl23j6D0=
dependencies:
sax "1.2.x"
xmlbuilder "8.2.x"
xregexp@2.0.0: xregexp@2.0.0:
version "2.0.0" version "2.0.0"
resolved "https://registry.yarnpkg.com/xregexp/-/xregexp-2.0.0.tgz#52a63e56ca0b84a7f3a5f3d61872f126ad7a5943" resolved "https://registry.yarnpkg.com/xregexp/-/xregexp-2.0.0.tgz#52a63e56ca0b84a7f3a5f3d61872f126ad7a5943"