function apiAbort(obj) { writeOutput(serializeJSON(obj)); abort; } function readJsonBody() { raw = toString(getHttpRequestData().content); if (isNull(raw) || len(trim(raw)) EQ 0) return {}; try { parsed = deserializeJSON(raw); } catch(any e) { apiAbort({ OK=false, ERROR="bad_json", MESSAGE="Invalid JSON body" }); } if (!isStruct(parsed)) return {}; return parsed; } function normStr(v) { if (isNull(v)) return ""; return trim(toString(v)); } function resolveSingleBusiness(uuid, major) { var qBiz = queryExecute( "SELECT b.ID, b.Name, b.BrandColor, b.HeaderImageExtension FROM Businesses b JOIN BeaconShards bs ON b.BeaconShardID = bs.ID WHERE bs.UUID = ? AND b.BeaconMajor = ? LIMIT 1", [ { value=uuid, cfsqltype="cf_sql_varchar" }, { value=major, cfsqltype="cf_sql_smallint" } ], { datasource="payfrit" } ); if (qBiz.recordCount EQ 0) { return { Found=false, Error="not_found" }; } var headerImageURL = ""; if (len(qBiz.HeaderImageExtension)) { headerImageURL = "/uploads/headers/#qBiz.ID#.#qBiz.HeaderImageExtension#"; } return { Found = true, BusinessID = qBiz.ID, BusinessName = qBiz.Name, BrandColor = qBiz.BrandColor, HeaderImageURL = headerImageURL }; } data = readJsonBody(); // Check for batch request if (structKeyExists(data, "Beacons") && isArray(data.Beacons)) { results = []; for (beacon in data.Beacons) { uuid = normStr(structKeyExists(beacon, "UUID") ? beacon.UUID : ""); major = structKeyExists(beacon, "Major") && isNumeric(beacon.Major) ? int(beacon.Major) : 0; if (len(uuid) EQ 0 || major LTE 0) { arrayAppend(results, { UUID=uuid, Major=major, BusinessID=javaCast("null",""), Error="invalid_params" }); continue; } resolved = resolveSingleBusiness(uuid, major); if (resolved.Found) { arrayAppend(results, { UUID = uuid, Major = major, BusinessID = resolved.BusinessID, BusinessName = resolved.BusinessName, BrandColor = resolved.BrandColor, HeaderImageURL = resolved.HeaderImageURL }); } else { arrayAppend(results, { UUID=uuid, Major=major, BusinessID=javaCast("null",""), Error="not_found" }); } } writeOutput(serializeJSON({ OK=true, COUNT=arrayLen(results), Results=results })); abort; } // Single request uuid = normStr(structKeyExists(data, "UUID") ? data.UUID : ""); major = 0; if (structKeyExists(data, "Major") && isNumeric(data.Major)) { major = int(data.Major); } // Also check URL params if (len(uuid) EQ 0 && structKeyExists(url, "UUID")) { uuid = normStr(url.UUID); } if (major LTE 0 && structKeyExists(url, "Major") && isNumeric(url.Major)) { major = int(url.Major); } if (len(uuid) EQ 0) { apiAbort({ OK=false, ERROR="missing_uuid", MESSAGE="UUID is required" }); } if (major LTE 0) { apiAbort({ OK=false, ERROR="missing_major", MESSAGE="Major is required" }); } resolved = resolveSingleBusiness(uuid, major); if (!resolved.Found) { apiAbort({ OK=false, ERROR="not_found", MESSAGE="No business found for this beacon" }); } #serializeJSON({ OK = true, BusinessID = resolved.BusinessID, BusinessName = resolved.BusinessName, BrandColor = resolved.BrandColor, HeaderImageURL = resolved.HeaderImageURL })# #serializeJSON({ OK=false, ERROR="server_error", MESSAGE=cfcatch.message, DETAIL=cfcatch.detail })#