Copy link to clipboard
Copied
Is there any way to make an XMLHttpRequest equivalent in Illustrator CS6 JavaScript?
I'd love to be able to have an Illustrator script make use of returned JSON. Is it possible? For instance, in plain old HTML and vanilla JavaScript, Id' do this:
<!DOCTYPE html>
<html lang="en-US">
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>AJAX</title>
<script type="text/javascript">
var xmlHttp = null;
xmlHttp = new XMLHttpRequest();
xmlHttp.open( "GET", "http://example.com", false );
xmlHttp.send( null );
var data = JSON.parse(xmlHttp.responseText);
alert(data.string);
</script>
</head>
<body style="background-color:#e5eecc;">
<div>Trying to grab some tasty JSON data.</div>
</body>
</html>
However, when I try a similar thing in a Illustrator script, I get "Error 22: XMLHttpRequest does not have a constructor."
I have full control over the server the JSON would be coming from if that helps.
Copy link to clipboard
Copied
Hi Tunna
As I do not work with JSON and HTML, I honestlly do not know exactelly what´s possible about this subject inside Illustrator via JavaScript
Anything I´d advice is: if you have the Extended Script Toolkit installed on your machine, look at the installation folder of this application (or search in your machine) by a manual called JavaScript Tools Guide.pdf.
I found on this link a version of this manual (but this is based in CS5): http://wwwimages.adobe.com/www.adobe.com/content/dam/Adobe/en/products/indesign/pdfs/JavaScriptTools...
Anyway, look at this manual. It shows things about http requests and XML integration into JavaScript for Illustrator.
Hope it helps a little
Best Regards
Gustavo.
Copy link to clipboard
Copied
Thnk you, Gustavo. It does not look like I am able to do what I want. Or, at least the way i wanted to do it.
Copy link to clipboard
Copied
Unfortunately ExtendScript for Illustrator is missing the Socket object.
You could eventually work around with a shell script via File.execute(), e.g. use the curl command.
Instead of JSON.parse you can use the JavaScript interpreter's eval(), it is less secure as it executes arbitrary code, but if you anyway control the source of your JSON that should not be a problem.
Copy link to clipboard
Copied
This is a very old thread (2013): If this post is still relevant I believe I have the answer you are looking for that works with .jsx
In After Effects, I get a json file from a url and parse it with jsx. Please let me know if you are interested.
Copy link to clipboard
Copied
AffterEffects also dose not have Socket Object. However, You can use CEP extension.
You can read references below:
Copy link to clipboard
Copied
I like using the script-only method using this brilliant code (& Bridge) : Loads data from a URL in Adobe Illustrator, synchronously! (Uses Bridge behind the scenes) · GitHub
Copy link to clipboard
Copied
sbaden11 wrote:
This is a very old thread (2013): If this post is still relevant I believe I have the answer you are looking for that works with .jsx
In After Effects, I get a json file from a url and parse it with jsx. Please let me know if you are interested.
if you have an alternative answer, by all means, please post your solution.
thanks in advance.
Copy link to clipboard
Copied
This is exactly what I use to pull .json files from a url in After Effects. I use this nearly every day - it works. I'm noticing that it does use a socket object. Sorry for the long code... I can push to Git if necessary
// This script requires that you download json and include it
#include "/Volumes/Documents/Scripts/json2.jsx"
var url = "http://feeds.nfl.com/feeds-rs/roster/3900.json"; // Sample NFL feed
var fileRepository = "/Volumes/Documents/feedRepository/JSON_FILES/"; // Local directory to save 3900.json file. I haven't figured out a way to just read the json file instead of downloading it.
var JSONFile = getJSONFile(url, fileRepository);
var jsonObj = JSON.parse(JSONFile);
buildPlayerObj(jsonObj);
function buildPlayerObj(obj){
// Do something with obj
}
////////////////////////////////////////////
// This code does all the work: I'm noticing that it uses socket
////////////////////////////////////////////
function getJSONFile(url, fileRepository){
if (kMaxRecursive301Calls == undefined){
const kMaxRecursive301Calls = 10; // Max level of nesting of HTTP 301 Moved Permanently
}
var fileName = url.split("/");
fileName = fileName[fileName.length - 1];
//var fileRepository = "/GFXM1/SCRIPTS/01 feedRepository/JSON_FILES/";
var imagePath = new File(fileRepository + fileName);
var imageData = GetURL(url,true);
if (imageData != null && imageData.body != null){
imagePath.open("w");
imagePath.encoding = "BINARY";
imagePath.write(imageData.body);
imagePath.close();
}
return imageData.body;
}
function GetURL(url,isBinary, recursive301CallLevel){
var reply = null;
const kUTF8CharState_Complete = 0;
const kUTF8CharState_PendingMultiByte = 1;
const kUTF8CharState_Binary = 2;
const kLineState_InProgress = 0;
const kLineState_SeenCR = 1;
const kProtocolState_Status = 1;
const kProtocolState_Headers = 2;
const kProtocolState_Body = 3;
const kProtocolState_Complete = 4;
const kProtocolState_TimeOut = 5;
do{
var parsedURL = ParseURL(url);
if (parsedURL.protocol != "HTTP"){ break; }
var socket = new Socket;
socket.timeout = 120;
if (! socket.open(parsedURL.address + ":" + parsedURL.port,"BINARY")){ break; }
if (isBinary){
var request =
"GET /" + parsedURL.path + " HTTP/1.0\n" +
"Host: " + parsedURL.address + "\n" +
"User-Agent: AfterEffects ExtendScript\n" +
"Accept: */*\n" +
"Connection: keep-alive\n\n";
}
else{
var request =
"GET /" + parsedURL.path + " HTTP/1.0\n" +
"Host: " + parsedURL.address + "\n" +
"User-Agent: AfterEffects ExtendScript\n" +
"Accept: text/xml,text/*,*/*\n" +
"Accept-Encoding:\n" +
"Connection: keep-alive\n" +
"Accept-Language: *\n" +
"Accept-Charset: utf-8\n\n";
}
socket.write(request);
var readState ={
buffer: "",
bufPos: 0,
curCharState: isBinary ? kUTF8CharState_Binary : kUTF8CharState_Complete,
curCharCode: 0,
pendingUTF8Bytes: 0,
lineState: kLineState_InProgress,
curLine: "",
line: "",
isLineReadyToProcess: false,
protocolState: kProtocolState_Status,
contentBytesPending: null,
dataAvailable: true,
status: "",
headers: {},
body: ""
};
while (! (readState.protocolState == kProtocolState_Complete && readState.buffer.length <= readState.bufPos) && readState.protocolState != kProtocolState_TimeOut){
if (readState.bufPos > 0 && readState.buffer.length == readState.bufPos){
readState.buffer = "";
readState.bufPos = 0;
}
if (readState.buffer == ""){
if (readState.protocolState == kProtocolState_Body){
if (readState.contentBytesPending == null){
if (! readState.dataAvailable && ! socket.connected){
socket = null;
readState.protocolState = kProtocolState_Complete;
}
else{
readState.buffer += socket.read();
readState.dataAvailable = readState.buffer.length > 0;
if (! readState.dataAvailable) {
readState.buffer += socket.read(1);
readState.dataAvailable = readState.buffer.length > 0;
}
}
}
else{
if (! readState.dataAvailable && ! socket.connected){
socket = null;
readState.protocolState = kProtocolState_TimeOut;
}
else{
readState.buffer = socket.read(readState.contentBytesPending);
readState.dataAvailable = readState.buffer.length > 0;
readState.contentBytesPending -= readState.buffer.length;
if (readState.contentBytesPending == 0){
readState.protocolState = kProtocolState_Complete;
socket.close();
socket = null;
}
if (isBinary){
readState.body += readState.buffer;
readState.buffer = "";
readState.bufPos = 0;
}
}
}
}
else if (readState.protocolState != kProtocolState_Complete){
if (! readState.dataAvailable && ! socket.connected){
socket = null;
readState.protocolState = kProtocolState_TimeOut;
}
else{
readState.buffer += socket.read(1);
readState.dataAvailable = readState.buffer.length > 0;
}
}
}
if (readState.buffer.length > readState.bufPos){
if (readState.curCharState == kUTF8CharState_Binary && readState.protocolState == kProtocolState_Body){
readState.body += readState.buffer;
readState.bufPos = readState.buffer.length;
}
else {
var cCode = readState.buffer.charCodeAt(readState.bufPos++);
switch (readState.curCharState){
case kUTF8CharState_Binary:
readState.curCharCode = cCode;
readState.multiByteRemaining = 0;
break;
case kUTF8CharState_Complete:
if (cCode <= 127){
readState.curCharCode = cCode;
readState.multiByteRemaining = 0;
}
else if ((cCode & 0xE0) == 0xC0){
readState.curCharCode = cCode & 0x1F;
readState.curCharState = kUTF8CharState_PendingMultiByte;
readState.pendingUTF8Bytes = 1;
}
else if ((cCode & 0xF0) == 0xE0){
readState.curCharCode = cCode & 0x0F;
readState.curCharState = kUTF8CharState_PendingMultiByte;
readState.pendingUTF8Bytes = 2;
}
else if ((cCode & 0xF8) == 0xF0){
readState.curCharCode = cCode & 0x07;
readState.curCharState = kUTF8CharState_PendingMultiByte;
readState.pendingUTF8Bytes = 3;
}
else{
readState.curCharCode = cCode;
readState.pendingUTF8Bytes = 0;
}
break;
case kUTF8CharState_PendingMultiByte:
if ((cCode & 0xC0) == 0x80){
readState.curCharCode = (readState.curCharCode << 6) | (cCode & 0x3F);
readState.pendingUTF8Bytes--;
if (readState.pendingUTF8Bytes == 0){ readState.curCharState = kUTF8CharState_Complete; }
}
else{
readState.curCharCode = cCode;
readState.multiByteRemaining = 0;
readState.curCharState = kUTF8CharState_Complete;
}
break;
}
if (readState.curCharState == kUTF8CharState_Complete || readState.curCharState == kUTF8CharState_Binary){
cCode = readState.curCharCode;
var c = String.fromCharCode(readState.curCharCode);
if (readState.protocolState == kProtocolState_Body || readState.protocolState == kProtocolState_Complete){
readState.body += c;
}
else{
if (readState.lineState == kLineState_SeenCR){
readState.line = readState.curLine;
readState.isLineReadyToProcess = true;
readState.curLine = "";
readState.lineState = kLineState_InProgress;
if (cCode == 13){ readState.lineState = kLineState_SeenCR; }
else if (cCode != 10){ readState.curLine += c; }
}
else if (readState.lineState == kLineState_InProgress){
if (cCode == 13){ readState.lineState = kLineState_SeenCR; }
else if (cCode == 10){
readState.line = readState.curLine;
readState.isLineReadyToProcess = true;
readState.curLine = "";
}
else{ readState.curLine += c; }
}
if (readState.isLineReadyToProcess){ readState.isLineReadyToProcess = false;
if (readState.protocolState == kProtocolState_Status){
readState.status = readState.line;
readState.protocolState = kProtocolState_Headers;
}
else if (readState.protocolState == kProtocolState_Headers){
if (readState.line == ""){ readState.protocolState = kProtocolState_Body; }
else{
var headerLine = readState.line.split(":");
var headerTag = headerLine[0].replace(/^\s*(.*\S)\s*$/,"$1");
headerLine = headerLine.slice(1).join(":");
headerLine = headerLine.replace(/^\s*(.*\S)\s*$/,"$1");
readState.headers[headerTag] = headerLine;
if (headerTag == "Content-Length"){ readState.contentBytesPending = parseInt(headerLine);
if (isNaN(readState.contentBytesPending) || readState.contentBytesPending <= 0){ readState.contentBytesPending = null; }
else{ readState.contentBytesPending -= (readState.buffer.length - readState.bufPos); }
}
}
}
}
}
}
}
}
}
if (socket != null){
socket.close();
socket = null;
}
reply = {
status: readState.status,
headers: readState.headers,
body: readState.body
};
}
while (false);
if (reply.status.indexOf("301") >= 0){
if (recursive301CallLevel == undefined){ recursive301CallLevel = 0; }
if (recursive301CallLevel < kMaxRecursive301Calls){ reply = GetURL(reply.headers.Location, isBinary, recursive301CallLevel + 1); }
}
return reply;
}
function ParseURL(url){
url=url.replace(/([a-z]*):\/\/([-\._a-z0-9A-Z]*)(:[0-9]*)?\/?(.*)/,"$1/$2/$3/$4");
url=url.split("/");
if (url[2] == "undefined") url[2] = "80"; var parsedURL = {
protocol: url[0].toUpperCase(),
address: url[1],
port: url[2],
path: ""
};
url = url.slice(3);
parsedURL.path = url.join("/");
if (parsedURL.port.charAt(0) == ':'){ parsedURL.port = parsedURL.port.slice(1); }
if (parsedURL.port != ""){ parsedURL.port = parseInt(parsedURL.port); }
if (parsedURL.port == "" || parsedURL.port < 0 || parsedURL.port > 65535){ parsedURL.port = 80; }
parsedURL.path = parsedURL.path;
return parsedURL;
}
Find more inspiration, events, and resources on the new Adobe Community
Explore Now