Skip to content
Merged
2 changes: 2 additions & 0 deletions WordPress/build.gradle
Original file line number Diff line number Diff line change
Expand Up @@ -493,6 +493,8 @@ dependencies {
testImplementation(libs.assertj.core)
testImplementation(libs.kotlinx.coroutines.test)
testImplementation(libs.turbine)
testImplementation(libs.robolectric)
testImplementation(libs.androidx.test.core)

androidTestImplementation project(path:':libs:mocks')

Expand Down
114 changes: 106 additions & 8 deletions WordPress/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -581,6 +581,82 @@
android:pathPattern="/site-monitoring/.*"
android:scheme="http" />

<data
android:host="wordpress.com"
android:path="/read"
android:scheme="https" />

<data
android:host="wordpress.com"
android:path="/read"
android:scheme="http" />

<data
android:host="wordpress.com"
android:path="/discover"
android:scheme="https" />

<data
android:host="wordpress.com"
android:path="/discover"
android:scheme="http" />

<data
android:host="wordpress.com"
android:pathPattern="/read/feeds/.*"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Security: Overly broad pathPattern: The pattern /read/feeds/.* will match ANY path starting with /read/feeds/, including potentially malicious paths like /read/feeds/../../../etc/passwd. While Android's intent filtering doesn't typically allow path traversal attacks, consider using more specific patterns.

The security scanner flagged these data tags as having non-unique attributes. While this is a warning, it might be cleaner to be more explicit with your intent filters. However, this is likely acceptable for your use case.

android:scheme="https" />

<data
android:host="wordpress.com"
android:pathPattern="/read/feeds/.*"
android:scheme="http" />

<data
android:host="wordpress.com"
android:pathPattern="/reader/feeds/.*"
android:scheme="https" />

<data
android:host="wordpress.com"
android:pathPattern="/reader/feeds/.*"
android:scheme="http" />

<data
android:host="wordpress.com"
android:path="/read/search"
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" />

<data
android:host="wordpress.com"
android:path="/read/search"
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" />

<data
android:host="wordpress.com"
android:path="/reader/search"
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" />

<data
android:host="wordpress.com"
android:path="/reader/search"
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" />

<data
android:host="wordpress.com"
android:pathPattern="/tag/.*"
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" />

<data
android:host="wordpress.com"
android:pathPattern="/tag/.*"
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" />

</intent-filter>
</activity-alias>

Expand Down Expand Up @@ -612,49 +688,71 @@
<data
android:host="wordpress.com"
android:pathPattern="/read/feeds/.*/posts/.*"
android:scheme="https" >
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" >
Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Moving the ignore suppression here instead of having a huuuge lint/baseline file

</data>

<data
android:host="wordpress.com"
android:pathPattern="/read/feeds/.*/posts/.*"
android:scheme="http" >
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="wordpress.com"
android:pathPattern="/read/blogs/.*/posts/.*"
android:scheme="https" >
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="wordpress.com"
android:pathPattern="/read/blogs/.*/posts/.*"
android:scheme="http" >
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="*.wordpress.com"
android:pathPattern="/2.../../../.*"
android:scheme="https" >
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="*.wordpress.com"
android:pathPattern="/2.../../../.*"
android:scheme="http" >
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="*.wordpress.com"
android:pathPattern="/19../../../.*"
android:scheme="https" >
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="*.wordpress.com"
android:pathPattern="/19../../../.*"
android:scheme="http" >
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="wordpress.com"
android:pathPattern="/reader/feeds/.*/posts/.*"
android:scheme="https"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<data
android:host="wordpress.com"
android:pathPattern="/reader/feeds/.*/posts/.*"
android:scheme="http"
tools:ignore="IntentFilterUniqueDataAttributes" >
</data>

<action android:name="org.wordpress.android.action.VIEW_POST" />
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -338,6 +338,43 @@
context.startActivity(intent);
}

public static void viewReaderDiscoverInNewStack(Context context) {

Check notice

Code scanning / Android Lint

Nullable/NonNull annotation missing on method parameter Note

Missing null annotation
Intent intent = getMainActivityInNewStack(context);
intent.putExtra(WPMainActivity.ARG_OPEN_PAGE, WPMainActivity.ARG_READER);
intent.putExtra(WPMainActivity.ARG_READER_DISCOVER_TAB, true);
context.startActivity(intent);
}

public static void viewReaderFeedInNewStack(Context context, long feedId) {
Intent mainActivityIntent = getMainActivityInNewStack(context)
.putExtra(WPMainActivity.ARG_OPEN_PAGE, WPMainActivity.ARG_READER);
Intent feedIntent = ReaderActivityLauncher.buildReaderFeedIntent(context, feedId, "deeplink");
TaskStackBuilder.create(context)
.addNextIntent(mainActivityIntent)
.addNextIntent(feedIntent)
.startActivities();
}

public static void viewReaderSearchInNewStack(Context context) {
Intent mainActivityIntent = getMainActivityInNewStack(context)
.putExtra(WPMainActivity.ARG_OPEN_PAGE, WPMainActivity.ARG_READER);
Intent searchIntent = ReaderActivityLauncher.createReaderSearchIntent(context);
TaskStackBuilder.create(context)
.addNextIntent(mainActivityIntent)
.addNextIntent(searchIntent)
.startActivities();
}

public static void viewReaderTagInNewStack(@NonNull Context context, @NonNull String tagSlug) {
Intent mainActivityIntent = getMainActivityInNewStack(context)
.putExtra(WPMainActivity.ARG_OPEN_PAGE, WPMainActivity.ARG_READER);
Intent tagIntent = ReaderActivityLauncher.buildReaderTagIntent(context, tagSlug, "deeplink");
TaskStackBuilder.create(context)
.addNextIntent(mainActivityIntent)
.addNextIntent(tagIntent)
.startActivities();
}

public static void viewPostDeeplinkInNewStack(Context context, Uri uri) {
Intent mainActivityIntent = getMainActivityInNewStack(context)
.putExtra(WPMainActivity.ARG_OPEN_PAGE, WPMainActivity.ARG_READER);
Expand Down Expand Up @@ -515,7 +552,7 @@

public static PendingIntent buildStatsPendingIntentOverMainActivityInNewStack(Context context, SiteModel site,
@Nullable StatsTimeframe timeframe,
@Nullable String period,

Check notice

Code scanning / Android Lint

Nullable/NonNull annotation missing on method parameter Note

Missing null annotation
@Nullable NotificationType type,
@NonNull
StatsLaunchedFrom launchedFrom,
Expand Down Expand Up @@ -1554,7 +1591,7 @@
parentIntent.addFlags(Intent.FLAG_ACTIVITY_NO_ANIMATION);
final Intent intent = new Intent(context, PostSignupInterstitialActivity.class);
TaskStackBuilder.create(context).addNextIntent(parentIntent).addNextIntent(intent).startActivities();
}

Check notice

Code scanning / Android Lint

Nullable/NonNull annotation missing on method parameter Note

Missing null annotation

public static void viewStatsSinglePostDetails(Context context, SiteModel site, PostModel post) {
if (post == null || site == null) {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,11 @@
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenPages
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenPagesForSite
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenQRCodeAuthFlow
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenFeedInReader
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenReader
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenReaderDiscover
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenReaderSearch
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenTagInReader
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenStats
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenStatsForSite
import org.wordpress.android.ui.deeplinks.DeepLinkNavigator.NavigateAction.OpenStatsForSiteAndTimeframe
Expand All @@ -37,7 +41,7 @@
@Inject constructor(private val activityNavigator: ActivityNavigator) {
@Suppress("ComplexMethod", "LongMethod")
fun handleNavigationAction(navigateAction: NavigateAction, activity: AppCompatActivity) {
when (navigateAction) {

Check warning on line 44 in WordPress/src/main/java/org/wordpress/android/ui/deeplinks/DeepLinkNavigator.kt

View check run for this annotation

SonarQubeCloud / SonarCloud Code Analysis

Reduce the number of when branches from 32 to at most 30.

See more on https://sonarcloud.io/project/issues?id=wordpress-mobile_WordPress-Android&issues=AZrZoGbWx9bj30CvRc7f&open=AZrZoGbWx9bj30CvRc7f&pullRequest=22374
LoginForResult -> ActivityLauncher.loginForDeeplink(activity)
StartCreateSiteFlow -> {
ActivityLauncher.showMainActivityAndSiteCreationActivity(activity, DEEP_LINK)
Expand Down Expand Up @@ -78,6 +82,10 @@
)

OpenReader -> ActivityLauncher.viewReaderInNewStack(activity)
OpenReaderDiscover -> ActivityLauncher.viewReaderDiscoverInNewStack(activity)
OpenReaderSearch -> ActivityLauncher.viewReaderSearchInNewStack(activity)
is OpenFeedInReader -> ActivityLauncher.viewReaderFeedInNewStack(activity, navigateAction.feedId)
is OpenTagInReader -> ActivityLauncher.viewReaderTagInNewStack(activity, navigateAction.tagSlug)
is OpenInReader -> ActivityLauncher.viewPostDeeplinkInNewStack(activity, navigateAction.uri.uri)
is ViewPostInReader -> ActivityLauncher.viewReaderPostDetailInNewStack(
activity,
Expand Down Expand Up @@ -123,6 +131,10 @@
data class OpenEditorForPost(val site: SiteModel, val postId: Int) : NavigateAction()
data class OpenEditorForSite(val site: SiteModel) : NavigateAction()
object OpenReader : NavigateAction()
object OpenReaderDiscover : NavigateAction()
object OpenReaderSearch : NavigateAction()
data class OpenFeedInReader(val feedId: Long) : NavigateAction()
data class OpenTagInReader(val tagSlug: String) : NavigateAction()
data class OpenInReader(val uri: UriWrapper) : NavigateAction()
data class ViewPostInReader(val blogId: Long, val postId: Long, val uri: UriWrapper) : NavigateAction()
object OpenEditor : NavigateAction()
Expand Down
Loading