Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2caa345d authored by Aayush Gupta's avatar Aayush Gupta
Browse files

Merge branch '4945-pwa_broadcast' into 'master'

PWA Player: Send PWA installation status as broadcast to all eligible apps

See merge request !2
parents 939f9f62 26d2a7a0
Loading
Loading
Loading
Loading
Loading
+82 −0
Original line number Diff line number Diff line
/*
 * Copyright (C) 2022  ECORP
 *
 * This program is free software: you can redistribute it and/or modify
 * it under the terms of the GNU General Public License as published by
 * the Free Software Foundation, either version 3 of the License, or
 * (at your option) any later version.
 *
 * This program is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
 * GNU General Public License for more details.
 *
 * You should have received a copy of the GNU General Public License
 * along with this program.  If not, see <https://www.gnu.org/licenses/>.
 */

package foundation.e.pwaplayer.broadcast

import android.app.Application
import android.content.ComponentName
import android.content.Context
import android.content.Intent

/**
 * This class is responsible for sending PWA install / removal status to all apps.
 * The sent intent contains following extras:
 * 1. SHORTCUT_ID - string shortcut id.
 * 2. URL - string url of the pwa.
 *
 * An app should declare a broadcast receiver in the manifest as below:
 * ```
 * <receiver android:name=".receiver.PWAPlayerStatusReceiver"
 *     android:exported="true">
 *     <intent-filter>
 *         <action android:name="foundation.e.pwaplayer.PWA_ADDED" />
 *     </intent-filter>
 *     <intent-filter>
 *         <action android:name="foundation.e.pwaplayer.PWA_CHANGED" />
 *     </intent-filter>
 *     <intent-filter>
 *         <action android:name="foundation.e.pwaplayer.PWA_REMOVED" />
 *     </intent-filter>
 *     </receiver>
 * ```
 * This class will be able to manually resolve the eligible broadcast receivers in all apps
 * and send them the broadcast.
 */
object PWAStatusBroadcast {

    private fun broadcast(application: Application, action: String, shortcutId: String, url: String) {
        try {
            val pm = application.packageManager
            val intent = Intent(action).apply {
                putExtra("SHORTCUT_ID", shortcutId)
                putExtra("URL", url)
            }
            pm.queryBroadcastReceivers(intent, 0).forEach {
                val component = ComponentName(it.activityInfo.packageName, it.activityInfo.name)
                application.sendBroadcast(intent.setComponent(component))
            }
        }
        catch (e: Exception) {
            e.printStackTrace()
        }
    }

    fun broadcastPwaAdded(context: Context, shortcutId: String, url: String) {
        broadcast(context.applicationContext as Application,
            "foundation.e.pwaplayer.PWA_ADDED", shortcutId, url)
    }

    fun broadcastPwaChanged(context: Context, shortcutId: String, url: String) {
        broadcast(context.applicationContext as Application,
            "foundation.e.pwaplayer.PWA_CHANGED", shortcutId, url)
    }

    fun broadcastPwaRemoved(context: Context, shortcutId: String, url: String) {
        broadcast(context.applicationContext as Application,
            "foundation.e.pwaplayer.PWA_REMOVED", shortcutId, url)
    }
}
 No newline at end of file
+3 −0
Original line number Diff line number Diff line
@@ -11,6 +11,9 @@ interface PwaDao {
    @Query("SELECT * FROM pwa WHERE _id = :id")
    fun getById(id: Long): Cursor

    @Query("SELECT * FROM pwa WHERE shortcutId = :shortcutId")
    fun getById(shortcutId: String): Cursor

    @Insert(onConflict = OnConflictStrategy.REPLACE)
    fun insert(pwa: Pwa): Long

+32 −1
Original line number Diff line number Diff line
@@ -7,6 +7,7 @@ import android.content.UriMatcher
import android.database.Cursor
import android.net.Uri
import android.util.Log
import foundation.e.pwaplayer.broadcast.PWAStatusBroadcast
import foundation.e.pwaplayer.database.PwaDatabase
import foundation.e.pwaplayer.database.mapToPwa
import foundation.e.pwaplayer.provider.PwaConstants.Companion.TABLE_NAME
@@ -51,6 +52,7 @@ class PwaProvider : ContentProvider() {
                }
                val uri = ContentUris.withAppendedId(uri, id)
                notifyListeners(uri)
                PWAStatusBroadcast.broadcastPwaAdded(context, pwa.shortcutId, pwa.url)
                return uri
            }
            else -> throw IllegalArgumentException("Invalid URI: Insert failed $uri")
@@ -118,6 +120,7 @@ class PwaProvider : ContentProvider() {
                val count = pwas.update(pwa)
                if (count > 0) {
                    notifyListeners(uri)
                    PWAStatusBroadcast.broadcastPwaChanged(context, pwa.shortcutId, pwa.url)
                }
                return count
            }
@@ -136,9 +139,25 @@ class PwaProvider : ContentProvider() {
        val pwas = PwaDatabase.getInstance(context).pwaDao()
        when (uriMatcher.match(uri)) {
            CODE_PWA_ITEM -> {
                val count = pwas.delete(ContentUris.parseId(uri))
                val id = ContentUris.parseId(uri)
                /*
                 * Attempt to get PWA info to send via broadcast before deleting it.
                 * TODO : VERIFY IF THIS WORKS
                 * This is an attempt to get the string shortcutId. Not sure if this works.
                 */
                val (shortcutId: String, url: String) = try {
                    val cursor = pwas.getById(ContentUris.parseId(uri))
                    cursor.moveToFirst()
                    val pwa = cursor.mapToPwa()
                    Pair(pwa.shortcutId, pwa.url)
                } catch (e: Exception) {
                    e.printStackTrace()
                    Pair("", "")
                }
                val count = pwas.delete(id)
                if (count > 0) {
                    notifyListeners(uri)
                    PWAStatusBroadcast.broadcastPwaRemoved(context, shortcutId, url)
                }
                return count
            }
@@ -147,9 +166,21 @@ class PwaProvider : ContentProvider() {
                    throw IllegalArgumentException("Invalid URI: cannot delete without ID $uri")
                else {
                    Log.d(TAG, "delete: ${selectionArgs[0]}")
                    /*
                     * Attempt to get PWA info to send via broadcast before deleting it.
                     */
                    val url: String = try {
                        val cursor = pwas.getById(selectionArgs[0])
                        cursor.moveToFirst()
                        cursor.mapToPwa().url
                    } catch (e: Exception) {
                        e.printStackTrace()
                        ""
                    }
                    val count = pwas.delete(selectionArgs[0])
                    if (count > 0) {
                        notifyListeners(uri)
                        PWAStatusBroadcast.broadcastPwaRemoved(context, selectionArgs[0], url)
                    }
                    return count
                }