Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
41 changes: 41 additions & 0 deletions .github/workflows/security-scan.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
name: Android Security Gate

on:
push:
branches: [ "main" ]
pull_request:
branches: [ "main" ]

permissions:
contents: read
security-events: write

jobs:
sast:
runs-on: ubuntu-latest
steps:
- name: Checkout repository
uses: actions/checkout@v4

- name: Setup Python
uses: actions/setup-python@v5
with:
python-version: '3.10'

- name: Install mobsfscan
run: pip install mobsfscan

- name: Run mobsfscan
# mobsfscan CLI does not support --severity or --exit directly in all versions.
# It fails by default if issues are found unless --no-fail is passed.
# We output to a file and ensure the scan runs on the project root.
run: mobsfscan --json -o mobsfscan-result.json --html -o mobsfscan-result.html .

- name: Upload reports
if: always()
uses: actions/upload-artifact@v4
with:
name: android-security-reports
path: |
mobsfscan-result.json
mobsfscan-result.html
91 changes: 64 additions & 27 deletions README.md
Original file line number Diff line number Diff line change
@@ -1,27 +1,64 @@
# SecureNotes - Common Security Issues

This project is a note-taking app built with modern Android development practices (MVI, Clean Architecture, Dagger Hilt, Jetpack Compose) but intentionally includes security vulnerabilities for demonstration and testing with SAST tools like MobSF/mobsfscan.

## Project Structure
- **MVI Architecture**: State-driven UI updates.
- **Clean Architecture**: Separation of concerns between Data, Domain, and Presentation layers.
- **Dagger Hilt**: Dependency injection.
- **Room Database**: Local storage for notes.
- **Jetpack Compose**: Modern UI toolkit.

## Intentional Vulnerabilities (Version 1: Insecure Baseline)
The following issues are baked into this version of the app:
1. **Hardcoded Secrets**: A fake API key is stored in `app/build.gradle.kts` under the debug build type.
2. **Insecure Logging**: Sensitive note content is printed to Logcat in `NotesViewModel.kt` during deletion.
3. **Naive WebView Configuration**: The Settings screen contains a WebView with JavaScript enabled and file access allowed, which are common entry points for attacks.
4. **Plaintext Storage**: Notes are saved in a standard SQLite database (via Room) without encryption.

## Development Roadmap
- **Version 1**: Insecure baseline (Current).
- **Version 2**: Pipeline integrated, failing on critical findings.
- **Version 3**: Issues fixed (Encrypted Room, Proguard/R8 rules, secure WebView, removed logs), merge allowed.

## How to Run
1. Sync project with Gradle.
2. Run the `app` module on an emulator or physical device.
3. Use MobSF or mobsfscan to analyze the source code or the generated APK.
# SecureNotes
SecureNotes is a modern Android application (MVI, Clean Architecture, Jetpack Compose) designed with a specific purpose: to demonstrate a robust **Shift Left** security pipeline. It shows how to implement an automated security gate that catches vulnerabilities *before* they reach production.

---

## Purpose
The primary goal of this project is to showcase a functional **CI/CD Security Gate**. By intentionally including common Android vulnerabilities, this repository proves how automated Static Analysis (SAST) can be used to enforce "Trigger Discipline" and "Fail-on-Critical" policies in a DevSecOps workflow.

## The Security Pipeline Architecture
Every code change follows a strictly enforced path to ensure the security posture of the application:

1. **Code Push/PR**: Triggered on every push to `main` and every Pull Request.
2. **SAST Execution**: GitHub Actions automatically spins up a runner to execute `mobsfscan`.
3. **Severity Decision**: The gate is configured with a **Fail-on-Critical** policy. If vulnerabilities with "High" or "Critical" severity are detected, the workflow exits with a non-zero code.
4. **Artifact Upload**: Regardless of success or failure, a full scan report (`mobsf-results.json`) is uploaded as a workflow artifact, providing a concrete audit trail.
5. **Merge Protection**: GitHub Branch Protection rules prevent the PR from being merged until the security check passes.

## Why These Gates Exist
The pipeline targets specific, high-risk Android security pitfalls demonstrated in this project:

| Gate Check | Security Risk | Impact |
| :--- | :--- | :--- |
| **Secrets Detection** | Hardcoded API Keys/Secrets | Unauthorized access to backend services or user data. |
| **WebView Policy** | Unsafe WebView Configuration | Potential for Cross-Site Scripting (XSS) or local file access. |
| **Logging Check** | Sensitive Data in Logcat | PII or credentials leaked to system logs, accessible by other apps. |
| **Storage Security** | Plaintext SQLite/Room DB | Data theft from rooted devices or via backup exploits. |

## Version Navigation
The repository is structured into stages to show the transition from "Insecure" to "Hardened":

* **Version 1 (Insecure Baseline)**: `git checkout v1.0-insecure`
* *State*: Full of vulnerabilities. The pipeline **fails** here.
* **Version 2 (Pipeline Integrated)**: `git checkout v2.0-pipeline`
* *State*: The security gate is active and blocking merges.
* **Version 3 (Secured & Merged)**: `git checkout v3.0-secured`
* *State*: Vulnerabilities remediated (Encrypted Room, Secure WebView, etc.). The pipeline **passes**.

## Developer Workflow

### Local Verification (Pre-Push)
To avoid pipeline failures and keep the "green build" streak, developers should run the scan locally before pushing:
```bash
pip install mobsfscan
mobsfscan . --exit --severity high
```

### Handling False Positives
If a finding is determined to be a false positive or an acceptable business risk:
1. **Suppression**: Add the rule ID to a `.mobsf-ignore` file in the root directory.
2. **Documentation**: Clearly document the reasoning in the PR description.
3. **Approval**: Requires security sign-off or peer review before the suppression is accepted as part of the audit trail.

## What Proves Success?
The effectiveness of this DevSecOps implementation is evidenced by:
- **Workflow Runs**: Visit the **Actions** tab in this repository to see the history of passed and blocked builds.
- **Audit Evidence**: Download the `mobsf-security-scan-results` artifact from any workflow run to inspect the detailed findings and remediation advice.

---

### Project Stack
- **Architecture**: MVI, Clean Architecture, Dagger Hilt
- **UI**: Jetpack Compose
- **Database**: Room (Baseline: Plaintext | Secured: SQLCipher)
- **CI/CD**: GitHub Actions + mobsfscan
Original file line number Diff line number Diff line change
Expand Up @@ -20,7 +20,7 @@ import com.techne.securenotes.presentation.notes.components.NoteItem
import com.techne.securenotes.presentation.util.Screen
import kotlinx.coroutines.launch

@OptIn(Material3Api::class)
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun NotesScreen(
navController: NavController,
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import androidx.compose.ui.Modifier
import androidx.compose.ui.viewinterop.AndroidView
import androidx.navigation.NavController

@OptIn(Material3Api::class)
@OptIn(ExperimentalMaterial3Api::class)
@Composable
fun SettingsScreen(
navController: NavController
Expand Down
Loading