Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Get unofficialStore threat while installing app from Visual Studio App Center #3

Closed
privaterepo2021 opened this issue Jan 25, 2023 · 13 comments
Assignees
Labels
enhancement New feature or request

Comments

@privaterepo2021
Copy link

Is there a way to add Visual Studio App Center to the supportedAlternativeStores array list?

@privaterepo2021 privaterepo2021 added the enhancement New feature or request label Jan 25, 2023
@msikyna
Copy link
Member

msikyna commented Jan 25, 2023

Hello @privaterepo2021 ,

the supportedAlternativeStores accepts a package name of the application, which installs your app. If you are downloading the APK from App Center, it might be installed by Android package installer. Try to include the com.google.android.packageinstaller or com.android.packageinstaller. However, this will allow installing your APK directly even not from App Center, therefore do not use it later in production.
Let us know, if it helped.

Kind regards,
Matúš, Talsec developer

@privaterepo2021
Copy link
Author

Hi @msikyna, thank you for the quick response. I had tried out the solution and it works.

@privaterepo2021
Copy link
Author

Hi @msikyna, I just checked that actually the plugin did not show unofficial store threat because the plugin has fail to init.

This is my configuration:

"tlacConfig": {
"androidConfig" : {
"packageName" : "com.eb.sps",
"certificateHash" : "2ZYTL+Z2gGVzO1QZ2VcMZ1GT1pebaNKFFoE+LVJd0AI=",
"supportedAlternativeStores": [
"com.google.android.packageinstaller",
"com.android.packageinstaller"
]
},
"iosConfig" : {
"appBundleIds": "com.eb.sps",
"appTeamId": "BLT26AAEG2"
},
"watcherMail" : null
}

This is from the debugger:

D/PluginManager: getPlugin - put: TalsecPlugin
W/CordovaPlugin: Attempted to send a second callback for ID: TalsecPlugin451479080
Result was: "Invalid action"

@tompsota
Copy link
Member

Hello @privaterepo2021,

this is happening because your config is nested under tlacConfig key and therefore freeRASP is not able to parse it correctly.
A valid config would look like this:

    var config = {
        androidConfig : {
            packageName : "com.eb.sps",
            certificateHash : "2ZYTL+Z2gGVzO1QZ2VcMZ1GT1pebaNKFFoE+LVJd0AI=",
            supportedAlternativeStores : [
                "com.google.android.packageinstaller",
                "com.android.packageinstaller"
            ]
        },
        iosConfig : {
            appBundleIds : "com.eb.sps",
            appTeamId : "BLT26AAEG2"
        },
        watcherMail : null 
    };

Try to pass object with this structure into talsec.start and let us know if that helped.

(Also don't forget to update the watcherMail ;) )

Best,
Tomas, Talsec developer

@privaterepo2021
Copy link
Author

privaterepo2021 commented Jan 27, 2023

Hi @tompsota, I had check the plugin code, looks like supportedAlternativeStores is not supported for the current master branch of this plugin? I notice that the config value is null for supportedAlternativeStores.

private fun parseTalsecConfigThrowing(configJson: String): TalsecConfig {
       val json = JSONObject(configJson)
       val androidConfig = json.getJSONObject("androidConfig")
       val packageName = androidConfig.getString("packageName")
       val certificateHash = androidConfig.getString("certificateHash")
       val watcherMail = json.getString("watcherMail")
       val alternativeStores = mutableListOf<String>()
       if (androidConfig.has("supportedAlternativeStores")) {
           val stores = androidConfig.getJSONArray("supportedAlternativeStores")
           for (i in 0 .. stores.length()) {
               alternativeStores.add(stores.getString(i))
           }
       }
       return TalsecConfig(packageName, certificateHash, watcherMail, null)
}

this is my function

initTLAC(){
        var config = {
            "androidConfig" : {
                "packageName" : "com.eb.sps", 
                "certificateHash" : "2ZYTL+Z2gGVzO1QZ2VcMZ1GT1pebaNKFFoE+LVJd0AI=",
                "supportedAlternativeStores": [
                    "com.google.android.packageinstaller",
                    "com.android.packageinstaller"
                ]
            },
            "iosConfig" : {
                "appBundleIds": "com.eb.sps",
                "appTeamId": "BLT26AAEG2"
            },
            "watcherMail" : "[email protected]"
        }; //serverConfig["tlacConfig"];
        var threatListener = (threatType)=>{
            this.logService.log("threat", threatType);
            switch(threatType) {
                case "privilegedAccess": // Android & iOS
                    let isEnableEmulator = serverConfig["isEnableEmulator"];
                    if(window.device.isVirtual) {
                        if(!isEnableEmulator) {
                            this.showRootEmulatorErrorMessage();
                        }
                    }
                    break;
                case "debug": // Android & iOS
                case "simulator": // Android & iOS
                case "appIntegrity": // Android & iOS
                case "unofficialStore": // Android & iOS
                case "hooks": // Android & iOS
                case "device binding": // Android & iOS
                case "deviceID": // iOS only
                case "missingSecureEnclave": // iOS only
                case "passcodeChange": // iOS only
                case "passcode": // iOS only
                    this.showRootEmulatorErrorMessage();
                    break;
                default:
                    console.log('Unknown threat type detected: ' + threatType);
                    this.showRootEmulatorErrorMessage();
            }
        };

        window.talsec.start(config, threatListener).then(() => {
            this.logService.log('Talsec initialized.');
        }).catch((error) => {
            this.logService.log('Error during Talsec initialization: ', error);
            // this.showRootEmulatorErrorMessage();
        });
}

I had try with your suggestion but still hit the same error.
If I removed the supportedAlternativeStores array list then it can work.

@msikyna
Copy link
Member

msikyna commented Jan 27, 2023

Hi @privaterepo2021 ,

you are right, there was a slight bug in the master branch regarding the supportedAlternativeStores.. it will be fixed in a moment, as today, we are releasing a v2.0.0.

There will be one more API change, certificateHash is now certificateHashes : ["your_signing_certificate_hash_base64"]; see the array, it now supports more certificate hashes.

@privaterepo2021
Copy link
Author

Hi @msikyna, I will test it out with the new version of the plugin. Thanks, have a great day 👍

@privaterepo2021
Copy link
Author

Hi @msikyna @tompsota , I still got the error after upgrading to the latest 2.0.0 version. Is there anything I miss out?

W/CordovaPlugin: Attempted to send a second callback for ID: TalsecPlugin1771000586
    Result was: "Invalid action"
D/PluginManager: exec() call to unknown plugin: DeleteLaunchScreenCache
I/chromium: [INFO:CONSOLE(1)] "Error during Talsec initialization: ", source: file:///android_asset/www/static/js/main.840d2e30.js (1)

This is my function

initTLAC(){
        var config = {
            "androidConfig" : {
                "packageName" : "com.eb.sps", 
                "certificateHash" : ["2ZYTi+Z2PGVzO1QZcVcMZ1GTmpebaNKFFoE+LVJd0AI="],
                "supportedAlternativeStores": [
                    "com.google.android.packageinstaller",
                    "com.android.packageinstaller"
                ]
            },
            "iosConfig" : {
                "appBundleIds": "com.eb.sps",
                "appTeamId": "BLT26AAEG2"
            },
            "watcherMail" : "[email protected]"
        }; //serverConfig["tlacConfig"];
        var threatListener = (threatType)=>{
            this.logService.log("threat", threatType);
            switch(threatType) {
                case "privilegedAccess": // Android & iOS
                    let isEnableEmulator = serverConfig["isEnableEmulator"];
                    if(window.device.isVirtual) {
                        if(!isEnableEmulator) {
                            this.showRootEmulatorErrorMessage();
                        }
                    }
                    break;
                case "debug": // Android & iOS
                case "simulator": // Android & iOS
                case "appIntegrity": // Android & iOS
                case "unofficialStore": // Android & iOS
                case "hooks": // Android & iOS
                case "device binding": // Android & iOS
                case "deviceID": // iOS only
                case "missingSecureEnclave": // iOS only
                case "passcodeChange": // iOS only
                case "passcode": // iOS only
                    this.showRootEmulatorErrorMessage();
                    break;
                default:
                    console.log('Unknown threat type detected: ' + threatType);
                    this.showRootEmulatorErrorMessage();
            }
        };

        window.talsec.start(config, threatListener).then(() => {
            this.logService.log('Talsec initialized.');
        }).catch((error) => {
            this.logService.log('Error during Talsec initialization: ', error);
            // this.showRootEmulatorErrorMessage();
        });
}

@privaterepo2021
Copy link
Author

privaterepo2021 commented Jan 27, 2023

I using

"@angular/core": "11.0.2"
"cordova-android": "11.0.0"
"cordova-ios": "6.2.0"

config.xml

<platform name="android">
        <allow-intent href="market:*" />
        <preference name="android-targetSdkVersion" value="31" />
        <preference name="android-minSdkVersion" value="22" />
        <preference name="AndroidXEnabled" value="true" />
        <preference name="AndroidInsecureFileModeEnabled" value="true" />
        <preference name="AndroidWindowSplashScreenAnimatedIcon" value="res/icon/android/logo.xml" />
        <preference name="AndroidWindowSplashScreenBackground" value="#FFFFFF" />
        <icon density="ldpi" src="res/icon/android/icon-36-ldpi.png" />
        <icon density="mdpi" src="res/icon/android/icon-48-mdpi.png" />
        <icon density="hdpi" src="res/icon/android/icon-72-hdpi.png" />
        <icon density="xhdpi" src="res/icon/android/icon-96-xhdpi.png" />
        <icon density="xxhdpi" src="res/icon/android/icon-144-xxhdpi.png" />
        <icon density="xxxhdpi" src="res/icon/android/icon-192-xxxhdpi.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-ldpi/push_notification_icon.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-mdpi/push_notification_icon.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-hdpi/push_notification_icon.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-xhdpi/push_notification_icon.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-xxhdpi/push_notification_icon.png" />
        <resource-file src="res/icon/android/push_notification_icon.png" target="app/src/main/res/drawable-xxxhdpi/push_notification_icon.png" />
        <feature name="SocialSharing">
            <param name="android-package" value="nl.xservices.plugins.SocialSharing" />
        </feature>
        <edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application/activity[@android:name='MainActivity']">
            <activity android:windowSoftInputMode="adjustResize" />
        </edit-config>
        <edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application/service[@android:name='com.adobe.phonegap.push.FCMService']">
            <service android:exported="true" />
        </edit-config>
        <edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application/service[@android:name='com.adobe.phonegap.push.PushInstanceIDListenerService']">
            <service android:exported="true" />
        </edit-config>
        <edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application">
            <application android:allowBackup="false" />
        </edit-config>
        <edit-config file="app/src/main/AndroidManifest.xml" mode="merge" target="/manifest/application" xmlns:android="http://schemas.android.com/apk/res/android">
            <application android:preserveLegacyExternalStorage="true" />
            <application android:requestLegacyExternalStorage="true" />
        </edit-config>
        <preference name="CodePushDeploymentKey" value="3gv8CBCU9EIGRLWe6zsa-Fi86wrmmleURMuvlx" />
        <preference name="AndroidPersistentFileLocation" value="Compatibility" />
        <preference name="signatureHash" value="D996138BE6763C65733B541971570C6751939A979B68D28516813E2D525DD002" />
        <preference name="googleSignatureHash" value="F555229C2CECF68E8F29A76795E0B794F8B86E040B0FC738716B260A85CE9644" />
        <preference name="releaseSignatureHash" value="D996138BE6763C65733B541971570C6751939A979B68D28516813E2D525DD002" />
        <resource-file src="google-services.json" target="app/google-services.json" />
        <hook src="hooks/after_platform_add.js" type="after_platform_add" />
        <preference name="GradlePluginKotlinEnabled" value="true" />
        <preference name="GradlePluginKotlinCodeStyle" value="official" />
        <preference name="GradlePluginKotlinVersion" value="1.7.10" />
    </platform>

@tompsota
Copy link
Member

tompsota commented Jan 27, 2023

@privaterepo2021 There was a breaking change in the API in v2.0.0, please change certificateHash to certificateHashes in your config.

@privaterepo2021
Copy link
Author

Hi @tompsota thanks for pointing out the mistake, it works now 👍

@privaterepo2021
Copy link
Author

Hi @tompsota , are we able to add supportedAlternativeStores for ios config? Seems like IOS is also hitting unofficial store threat if I build Ipa from xcode

@msikyna
Copy link
Member

msikyna commented Feb 1, 2023

Hello @privaterepo2021 ,
the iOS only supports an official way (AppStore or TestFlight) of installing the application. Building an IPA from Xcode correctly hits the unofficial store threat.

Kind regards,
Matúš, Talsec developer

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
enhancement New feature or request
Projects
None yet
Development

No branches or pull requests

4 participants