Skip to content
Open
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
112 changes: 112 additions & 0 deletions AGENTS.CLOUD.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,112 @@
# AGENTS.md

## Cursor Cloud specific instructions
Comment on lines +1 to +3
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟡 Minor

Align heading with actual file name and hyphenation

Line 1 says # AGENTS.md in AGENTS.CLOUD.md, and Line 3 should read “Cloud-specific” for consistency/readability.

Suggested doc change
-# AGENTS.md
+# AGENTS.CLOUD.md

-## Cursor Cloud specific instructions
+## Cursor Cloud-specific instructions
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
# AGENTS.md
## Cursor Cloud specific instructions
# AGENTS.CLOUD.md
## Cursor Cloud-specific instructions
🧰 Tools
🪛 LanguageTool

[uncategorized] ~3-~3: When ‘Cloud-specific’ is used as a modifier, it is usually spelled with a hyphen.
Context: # AGENTS.md ## Cursor Cloud specific instructions ### Environment Overview ...

(SPECIFIC_HYPHEN)

🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@AGENTS.CLOUD.md` around lines 1 - 3, Update the top headers so they match the
file name and use consistent hyphenation: change the main header text "#
AGENTS.md" to "# AGENTS.CLOUD.md" and change the subheader "## Cursor Cloud
specific instructions" to "## Cursor Cloud-specific instructions" so the
document title and the Cloud-specific phrasing are consistent with the filename
and style.


### Environment Overview

This is the **Mattermost Mobile** React Native app (v2.39.0). The Cloud VM runs on Linux (no macOS/iOS support), so only **Android** builds and the **JS/TS toolchain** are available.
Comment thread
enahum marked this conversation as resolved.

### Key Commands (see CLAUDE.md for full list)

| Task | Command |
|---|---|
| Lint | `npm run lint` |
| TypeScript check | `npm run tsc` |
| Auto-fix lint | `npm run fix` |
| Unit tests | `npm run test` |
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

npm test

| Metro bundler | `npm start` |
| Android build | `cd android && ./gradlew installDebug -PreactNativeArchitectures=x86_64 --no-daemon` |

### Android SDK

- Installed at `/opt/android-sdk` with env vars in `~/.bashrc` (`ANDROID_HOME`, `ANDROID_SDK_ROOT`, `JAVA_HOME`, `PATH`).
- SDK components: platform-tools, platforms;android-35, build-tools;35.0.0, ndk;27.1.12297006, emulator, system-images;android-28;default;x86_64.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Probably best to read the tools and ndk versions from the gradle file as they will change in time

- **API 28 (default) or API 34** emulators are available. API 28 boots in ~70s and app starts in ~2min. API 34 boots in ~290s and app starts in ~5min. API 35 causes ANR crashes during startup due to strict process-start timeouts. Use API 28 for speed or API 34 for modern Android look.
Comment thread
enahum marked this conversation as resolved.

### Starting the Android Emulator (no KVM)

The Cloud VM lacks KVM, so the emulator runs in **software emulation** (`-accel off`). This is very slow — expect ~90s boot time and ~2min app startup.

```bash
export ANDROID_HOME=/opt/android-sdk
export PATH=$PATH:$ANDROID_HOME/cmdline-tools/latest/bin:$ANDROID_HOME/platform-tools:$ANDROID_HOME/emulator
export DISPLAY=:1

emulator -avd Pixel_API_28 -no-audio -gpu swiftshader_indirect \
-no-boot-anim -no-snapshot -memory 2048 -partition-size 4096 \
-accel off -no-metrics &
```

After boot, set up ADB reverse proxy:
```bash
adb reverse tcp:8081 tcp:8081 # Metro bundler
adb reverse tcp:8065 tcp:8065 # Mattermost server
```

### Installing the APK (fast method)

Do NOT use `adb install` directly — it's extremely slow on software emulation. Instead:
```bash
adb push /workspace/android/app/build/outputs/apk/debug/app-debug.apk /data/local/tmp/app-debug.apk
adb shell pm install -t /data/local/tmp/app-debug.apk
adb shell cmd package compile -m speed -f com.mattermost.rnbeta # dex optimization — takes ~5min but critical for startup speed
```

### Mattermost Server (Docker)

A local Mattermost Enterprise server runs via Docker for the mobile app to connect to:

```bash
# Ensure Docker daemon is running (sudo dockerd via tmux)
docker network create mattermost

# PostgreSQL
docker run -d --name mattermost-postgres --network mattermost \
-e POSTGRES_USER=mmuser -e POSTGRES_PASSWORD=mostest -e POSTGRES_DB=mattermost \
-p 5432:5432 postgres:15

# Mattermost Server (requires MM_TEST_LICENSE env secret)
docker run -d --name mattermost-server --network mattermost \
-e MM_SQLSETTINGS_DRIVERNAME=postgres \
-e "MM_SQLSETTINGS_DATASOURCE=postgres://mmuser:mostest@mattermost-postgres:5432/mattermost?sslmode=disable&connect_timeout=10" \
-e MM_SERVICESETTINGS_SITEURL=http://localhost:8065 \
-e MM_TEAMSETTINGS_ENABLEOPENSERVER=true \
-e MM_SERVICESETTINGS_ENABLELOCALMODE=true \
-e MM_SERVICESETTINGS_ENABLETESTING=true \
-e MM_SERVICESETTINGS_ENABLEDEVELOPER=true \
-e MM_SERVICEENVIRONMENT=test \
-e "MM_LICENSE=$MM_TEST_LICENSE" \
-p 8065:8065 \
mattermost/mattermost-enterprise-edition:master
```

**Critical:** `MM_SERVICEENVIRONMENT=test` is required for the test license to be accepted.

Test user: `admin` / `Admin1234!` (team: `test-team`, channel: `town-square`).

### npm install Gotchas

- The `preinstall` script runs `solidarity` checks that expect Android SDK env vars and iOS tooling. On the Cloud VM, use `npm install --ignore-scripts` followed by manual `npx patch-package && bash ./scripts/postinstall.sh`.
- The `postinstall` script copies Compass Icons font and sound assets — must run after install.

### Test Notes

- Jest tests: 551/552 suites pass. 2 snapshot failures in `app/components/formatted_date/index.test.tsx` for the `ko` locale are a pre-existing Node.js `Intl` formatting difference (Korean meridiem `오전` vs `AM`), not a code issue.
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Careful with this, we want to continue adding tests

- Build for Android with `-PreactNativeArchitectures=x86_64` to speed up builds (only targets the emulator arch).

### Interacting with the Emulator
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

Have you looked into integrating this with Maestro? Perhaps ot could write the end to end tests with Maestro and just run them?


- Standard `adb shell input text` does **NOT** work reliably with React Native TextInput components.
- Use the `mattermost://` deep link scheme to populate the server URL: `adb shell am start -a android.intent.action.VIEW -d "mattermost://localhost:8065" com.mattermost.rnbeta`. Note: this sets the URL without `http://` prefix; you still need to fill in "Display Name" to enable the Connect button.
- **Recommended:** Use the `@mobilenext/mobile-mcp` MCP server for full simulator interaction (taps, text input, screenshots). See CLAUDE.md for details on testing with mobile MCP.
- **Alternative:** Use the `computerUse` subagent with the emulator window visible on `DISPLAY=:1`. The `computerUse` subagent can click and type directly into the emulator GUI. Be aware the subagent accumulates screenshots and may hit the 100-image limit on long sessions.
- For posting messages when text input is difficult, you can use the Mattermost REST API directly — the app picks up new messages via WebSocket in real time.

### Docker Daemon

Docker is installed but the daemon must be started manually. Use a tmux session:
```bash
SESSION_NAME="dockerd"
tmux -f /exec-daemon/tmux.portal.conf new-session -d -s "$SESSION_NAME" -- sudo dockerd
```
After starting, fix socket permissions: `sudo chmod 666 /var/run/docker.sock`
Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

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

⚠️ Potential issue | 🟠 Major

Avoid world-writable Docker socket permissions

Line 112 recommends chmod 666 /var/run/docker.sock, which weakens host security significantly. Prefer group-based access instead (docker group) or rootless Docker.

Suggested doc change
-After starting, fix socket permissions: `sudo chmod 666 /var/run/docker.sock`
+After starting, prefer group-based Docker access instead of opening the socket to all users:
+`sudo usermod -aG docker "$USER"` (then re-login), or run Docker in rootless mode.
📝 Committable suggestion

‼️ IMPORTANT
Carefully review the code before committing. Ensure that it accurately replaces the highlighted code, contains no missing lines, and has no issues with indentation. Thoroughly test & benchmark the code to ensure it meets the requirements.

Suggested change
After starting, fix socket permissions: `sudo chmod 666 /var/run/docker.sock`
After starting, prefer group-based Docker access instead of opening the socket to all users:
`sudo usermod -aG docker "$USER"` (then re-login), or run Docker in rootless mode.
🤖 Prompt for AI Agents
Verify each finding against the current code and only fix it if needed.

In `@AGENTS.CLOUD.md` at line 112, Replace the instruction that recommends running
`chmod 666 /var/run/docker.sock` with guidance to avoid world-writable socket
permissions: advise adding the user to the `docker` group (e.g., `usermod -aG
docker <user>`), or configuring rootless Docker, or using more secure socket
ACLs (e.g., `setfacl`) or chown to the `docker` group so only authorized users
can access `/var/run/docker.sock`; explicitly state not to use `chmod 666` and
include a short note about security risks.

Loading