When running an Alloy project on a device or releasing an Adhoc or an App store version, thus running the project through a pipeline where Javascript files are additionally processed, odd behavior is observed where a block of code may not executed, without any compilation or runtime errors.
*Steps to reproduce:*
* Create a new default Alloy Project
* add example code below to in index.js controller
* run project on an iOS device (run directly, just without LiveView; or create and install an Adhoc build; or create and install AppStore build through Testflight)
*Expected result:*
* setTiProps function should've run in entirety and styling should be applied to the Label (correct_screenshot.png)
* OR if any part of the example Javascript is invalid, a compilation error or a runtime error should've been triggered
*Actual result:*
* setTiProps function is somehow not executed in its entirety and styling is thus not applied to the Label (incorrect_screenshot.png)
Additional observations - please note that this is *not* a styling issue
The correct and expected result is shown in the following cases:
* by running on an actual device _with_ LiveView enabled
* by running on an iOS simulator _with_ or _without_ LiveView
* most unexpectedly, by modifying the example code through inserting *any dummy line* into the setTiProps function just before the _for_ loop, such as: console.log("Here");
* (also, by compiling and running the code with SDK 7.4 and lower)
The above observations lead me to postulate that one of the steps active in additional Javascript processing for device builds (minimization, obfuscation, encryption, ...?) encounters a situation in the example code that causes it to silently modify the function in a way that it makes it not run all the way through, all without triggering any compilation or runtime errors - this makes it particularly challenging to track down the real issue as most attempts to debug the code will cause it run correctly again (either by modifying the code with log statements or creating a debug build that then skips the troublesome Javascript processing pipeline).
----
_index.js:_
var ALLOWED_PROPS = [
"backgroundColor",
"borderColor",
"borderRadius",
"borderWidth",
"height",
"width",
];
function setTiProps(args, component) {
if (!component) return;
var args = args || {}, prop = '';
for(var i = 0, j = ALLOWED_PROPS.length; i < j; i++){
prop = ALLOWED_PROPS[i];
if(typeof args[prop] !== "undefined") {
component[prop] = args[prop];
}
}
};
setTiProps({
"backgroundColor": "red",
"borderColor": "green",
"width": "100%",
"height": "50dp"
}, $.label);
function doClick(e) {
alert($.label.text);
}
$.index.open();
[~ravsec] firstly, thank you for such a complete bug report! I've took a look into this and it does look to be a problem with the package we use for minification (babel-minify), it appears that when minifying the
setTiProps
function it inlines the declaration ofargs
andprop
into the for loop definition (code below) I believe this is the root cause of the issue you're seeing.I was able to fix this without requiring disabling js minification by changing
setTiProp
to the following:Do you want to give that a try and let me know how it goes?
Thank you for your response Ewan. In the meantime I've refactored that particular piece of code to more modern standards as well - it was a very old piece of code as evidenced by the coding standards used :) That seemed to have avoided triggering the minimization bug. Your approach works well too!
I'm going to close this one out as the underlying issue was fixed