Quality-of-life addition to packager.bat

Since 2019 Packager.bat has modification to include required architecture:

:: which architecture?
echo.
echo Please select your target architecture for Android:
echo.
echo [1] armv7 ^(32-bit ARM devices^)
echo [2] x86 ^(Intel products^)
echo [3] armv8 ^(64-bit ARM devices^)
echo.
set /P ARCH=[Choice:]
echo.
if "%ARCH%"=="1" set OPTIONS=%OPTIONS% -arch armv7
if "%ARCH%"=="2" set OPTIONS=%OPTIONS% -arch x86
if "%ARCH%"=="3" set OPTIONS=%OPTIONS% -arch armv8

So, the typical process of building a release for Google play was:

  1. Run PackageApp.bat
  2. Select 3 (Android release with captive runtime), then select 1 (arm7)
  3. Rename the created file
  4. Run PackageApp.bat again
  5. Select 3 (Android release with captive runtime), then select 3 (arm7)

If you don’t rename the created apk on step 3, it would be overwritten by the apk created on step 5.

I did so many times, then I recalled Zwetan’s words “the programmer should not be afraid of .bat files”, and made a one-line modification. Instead of the string
set OUTPUT=%DIST_PATH%\%DIST_NAME%%TARGET%.%DIST_EXT%
I wrote
set OUTPUT=%DIST_PATH%\%DIST_NAME%%TARGET%-%ARCH%.%DIST_EXT%

So, now I get files “myGame-captive-runtime-1.apk” and “myGame-captive-runtime-2.apk” in my “dist” folder, and I submit them to Google Play at once together.

1 Like

well… about quality of life, you’re limiting yourself quite a lot by just using batch files

If you want, since the very beginning of Windows you got MS-DOS via COMMAND.COM (9x) and later cmd.exe (NT), and they all provided basic scripting on the CLI with Batch files (.bat), but that is very limited.

In 1998 Microsoft created Windows Scripting Host (WSH) to address all the shortcomings of Batch files, and later around 2002 from project Monad they finally released in 2006 PowerShell, again to provide more scripting power than Batch or WSH.

And even later in 2019, they released Windows Subsystem for Linux (WSL),
another brilliant concept where they kind of merge a Linux environment with a Windows environment, and since then they went all “crazy” updating the Windows CLI,
see their blog Windows Command Line where they talk about WSL, Windows Terminal and all the new stuff.

Windows Command Line
Windows Terminal, Console and Command-Line, Windows Subsystem for Linux, WSL

So yeah you can still use .bat but imho you’re making yourself a disservice

there are at least 3 alternatives

  • Windows Script Host (WSH)

    The Microsoft Windows Script Host (WSH) (formerly named Windows Scripting Host) is an automation technology for Microsoft Windows operating systems that provides scripting abilities comparable to batch files, but with a wider range of supported features.

    You can use 2 default scripting engine: VBScript or JScript
    shipped with Windows (installed by default) since Windows 98
    you can script HTML pages with the extension .hta and make little UI app
    (see HTML Application)

  • PowerShell

    PowerShell is a task automation and configuration management framework from Microsoft, consisting of a command-line shell and the associated scripting language. Initially a Windows component only, known as Windows PowerShell, it was made open-source and cross-platform on 18 August 2016 with the introduction of PowerShell Core. The former is built on the .NET Framework, the latter on .NET Core.

    shipped with Windows since Windows 7
    made open source and cross-platform in 2016

  • Windows Subsystem for Linux (WSL)
    with that you can use Bash or anything easily installable on a Linux distro with a one liner
    basically about any scripting or programming environment like Perl, PHP, Python, etc.
    and use those from Windows, see Windows interoperability with Linux


And two more things

because to compile AIR, you already need Java because all the compiler tools use Java
you could use Apache Ant to automate your build

In fact, the Flex SDK when merged with the AIR SDK provide Ant tasks
see:

<project name="Flex Ant Tasks Build Script" default="air">

    <!-- Load the environment-specific properties -->
    <property file="build.properties" />

    <!-- Sets the FlexTasks.jar file that contains the build tasks -->
    <taskdef resource="flexTasks.tasks" classpath="${FLEX_HOME}/ant/lib/flexTasks.jar"/> 

    <!-- Start off by recreating the deployment directory -->
    <target name="init">
        <delete dir="${DEPLOY_DIR}" />
        <mkdir dir="${DEPLOY_DIR}" />
    </target>

    <!-- Build and output the main SWF file - repeat this for each SWF in the solution -->
    <target name="compile" depends="init">
        <mxmlc  file="${SRC_DIR}/AntExample.mxml"
                output="${DEPLOY_DIR}/AntExample.swf"
                debug="${DEBUG}"
                optimize="${OPTIMIZE}"
                locale="${LOCALE}"
                configname="air">
            <load-config filename="${FLEX_HOME}/frameworks/flex-config.xml"/>
            <source-path path-element="${SRC_DIR}"/>
            <library-path dir="${FLEX_HOME}/frameworks/libs" includes="*.swc" append="true"/>
            <library-path dir="${FLEX_HOME}/frameworks/libs/air" includes="*.swc" append="true"/>
            <library-path dir="${FLEX_HOME}/frameworks/locale" includes="${LOCALE}" append="true"/>
        </mxmlc>
    </target>

    <!-- Now create the AIR package using the ADT utility -->
    <target name="air" description="Create the AIR package" depends="compile">
        <exec executable="${FLEX_HOME}/bin/adt.bat" failonerror="true">
            <arg line="-package" />
            <arg line="-tsa none" />
            <arg line="-storetype pkcs12" />
            <arg line="-keystore ${basedir}/keys/AntExample.p12" />
            <arg line="-storepass password" />
            <arg line="${DEPLOY_DIR}/AntExample.air" />
            <arg line="${SRC_DIR}/AntExample-app.xml" />
            <arg line="-C ${DEPLOY_DIR} AntExample.swf" />
        </exec>
    </target>

</project>

Last thing is about automation, basically you want to be able to remove any human intervention so any tool that works for you is good enough, but you also want a kind of minimum, to me here a few of those

  • be able to control other CLI tools
  • be able to have different workflow
    let’s say “build when I’m testing with the IDE”, “make a debug build to send to testers”, “make a release signed build”, etc.
  • if you need to use your mouse, select something, click something, move something
    it is not automated, you’re wasting precious time

With Ant (for example, but other tools would probably be similar) you could

  • automatically increment your build version
  • detect Windows / macOS / Linux and redirect to build a specific release
  • build many versions of the same app using different versions of SDK
    for ex: build a Windows 32-bit and a Windows 64-bit
  • unpack a file, modify something, repack the file
  • run tests after the build
    for ex with Android: apkanalyzer

There are many automation software out there and many much more powerful scripting environment than just Batch.

1 Like

Thank you for the detailed review! I’ll look deeper and will find a tool for the next automatization I have in mind.
When I deploy the same Android game to different stores, for the sake of analytics I have a string variable named platform, which can take values “GooglePlay”, “Amazon”, “Huawei”. Then I use this variable to send analytics events about plays on each platform.

So, the steps I take to produce game version for 3 platforms now look like this:

  1. in the MainConfig.as set the value of platform to “Google Play”
  2. Compile using ctrl+Enter
  3. Produce 32-bit apk for GP
  4. Produce 64-bit apk for GP
  5. in the MainConfig.as set the value of platform to “Amazon”
  6. Compile using ctrl+Enter
  7. Produce 32-bit apk for Amazon
  8. in the MainConfig.as set the value of platform to “Huawei”
  9. Compile using ctrl+Enter
  10. Produce 32-bit apk for Huawei

One day I will be tired of this routine enough to make good optimization :slight_smile:

Ant + bash will change your life if you master that for your builds.

3 Likes

you know the compilers can already manage that for you with conditional compilation

see this other post where I mention it

the scenario with Ant would be something like that

  • run the build with a parameter $ ant -Danalytics="Amazon"
  • when you call MXMLC, pass the value of the ant var to the compiler
    <arg line="-define+=CONFIG:Analytics,\"'${analytics}'\""/>
  • and in the AS3 code
    var analyticsPlatform:String = CONFIG:Analytics;

see Using conditional compilation (Web Archive)
or the PDF Using Adobe Flex 4.6 (page 2191)

you can use that in a lot of different way
if you have a lot of variables per platform you could use an external XML file

for ex: huawei.xml

<compiler>
  <define append="true">
    <name>CONFIG::Analytics</name>
    <value>'Huawei'</value>
  </define>
  <define append="true">
    <name>CONFIG::storeURL</name>
    <value>'https://www.somedomain.com'</value>
  </define>
</compiler>

and then use $ mxmlc -load-config+=huawei.xml
note the +=, it will use the original config and you will chain your own config to it
look at “About option precedence” (page 2174)

or with Ant you can copy a file from a template to a file you want to be compiled
but during the copy you can filter/replace tokens

<copy file="${basedir}/build/templates/${TARGET_PLATFORM}.as.tpl"
      tofile="${basedir}/${app.sources}/config/platform.as">
    <filterset>
        <filter token="ANALYTICS" value="${config.analytics}"/>
    </filterset>
</copy>

in template something.as.tpl

package something
{
    var analyticsPlatform:String = "@ANALYTICS@";
}

or switch ant properties file

ant or other, you can do a hell lot

+100 that

you could have a build.xml that does a lot of stuff in different targets
but let’s say you have a workflow where among all those targets
you want only to generate the documentation

you could have a small build_doc.sh

#!/bin/bash -e

ant -Dbuild.binaries=false \
    -Dbuild.documentation=true \
    -Dbuild.components=false \
    -Dbuild.verbose=true

and the ant XML would look like

    <target name="compile" depends="something,otherthing">

        <if>
            <equals arg1="${build.binaries}" arg2="true"/>
        <then>
            <antcall target="compile-binaries-task"/>
        </then>
        </if>

        <if>
            <equals arg1="${build.components}" arg2="true"/>
        <then>
            <antcall target="compile-components-task"/>
        </then>
        </if>

        <if>
            <equals arg1="${build.documentation}" arg2="true"/>
        <then>
            <antcall target="compile-documentation-task"/>
        </then>
        </if>
       ...

yep extremely powerful, so YMMV
some tools will fit better your workflow or preference than others
but bash and ant, yep those are in general the first to try

feel free to discuss all those automation tools and questions etc. in #cli
it is here for that

1 Like