Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
36 commits
Select commit Hold shift + click to select a range
b8f3823
Add socket interface and its TCP implementation
matheusfillipe May 30, 2025
04a26a1
WIP
matheusfillipe Jun 16, 2025
d895bee
Merge branch 'main' into feat/make-native-app-default-irc-application…
matheusfillipe Jun 16, 2025
311a721
Merge branch 'main' of https://github.com/ObsidianIRC/ObsidianIRC int…
matheusfillipe Sep 20, 2025
5d1374a
WIP
matheusfillipe Sep 21, 2025
9d9f10d
Merge branch 'main' of https://github.com/ObsidianIRC/ObsidianIRC int…
matheusfillipe Sep 29, 2025
4587df2
lint fixes
matheusfillipe Sep 29, 2025
b862583
Merge branch 'main' of https://github.com/ObsidianIRC/ObsidianIRC int…
matheusfillipe Oct 18, 2025
32ba697
functional
matheusfillipe Nov 13, 2025
dd6b760
fix lints
matheusfillipe Nov 13, 2025
2cc4432
fix build?
matheusfillipe Nov 13, 2025
aeb33e4
use rustls for android
matheusfillipe Nov 14, 2025
24e5016
fix url parsing manually because android webview is weird
matheusfillipe Nov 16, 2025
41f5dcb
reduce logging
matheusfillipe Nov 16, 2025
9b0afd6
fix url parser
matheusfillipe Nov 16, 2025
01ad445
fix IOS build
matheusfillipe Nov 16, 2025
e2e0ea4
open irc uris in obsidian
matheusfillipe Nov 16, 2025
113cb10
Mark "IRC" by default when opening irc urls
matheusfillipe Nov 16, 2025
c1c58c9
improve iphone fitting
matheusfillipe Nov 16, 2025
ce26a64
handle irc uris in iphone
matheusfillipe Nov 16, 2025
795d570
avoid capitalizing stuff
matheusfillipe Nov 16, 2025
7e58700
buffer until \r\n
matheusfillipe Nov 16, 2025
5a349f8
fix infinite rerender
matheusfillipe Nov 17, 2025
deb1256
Merge branch 'main' of https://github.com/ObsidianIRC/ObsidianIRC int…
matheusfillipe Dec 20, 2025
a8b2d53
update lockfile
matheusfillipe Dec 20, 2025
6166cdd
0.2.2
matheusfillipe Dec 20, 2025
e7a374f
add job to release android apk in playstore
matheusfillipe Dec 31, 2025
d3e968a
Merge branch 'main' of https://github.com/ObsidianIRC/ObsidianIRC int…
matheusfillipe Dec 31, 2025
a8383bd
fix(workflows): Formatting
matheusfillipe Dec 31, 2025
b2825ce
test publish
matheusfillipe Jan 3, 2026
40632cb
test production track
matheusfillipe Jan 4, 2026
a2ae5aa
0.2.3
matheusfillipe Jan 4, 2026
7ad40d4
prepare for production
matheusfillipe Jan 4, 2026
7f707e1
avoid version conflicts
matheusfillipe Jan 4, 2026
93cf1a5
testing and simplifying internal release
matheusfillipe Jan 4, 2026
f7a2296
everything looks good so far
matheusfillipe Jan 4, 2026
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
172 changes: 172 additions & 0 deletions .github/workflows/publish.yaml
Original file line number Diff line number Diff line change
Expand Up @@ -7,6 +7,11 @@ on:
tags:
- "v*.*.*"
workflow_dispatch:
inputs:
google-playstore-version:
description: 'Optional: Override Google Play version code'
required: false
type: string

jobs:
collect-version:
Expand Down Expand Up @@ -169,6 +174,7 @@ jobs:
uses: swatinem/rust-cache@v2
with:
workspaces: "./src-tauri -> target"
shared-key: "android-builds"

- name: Install dependencies
run: npm install
Expand Down Expand Up @@ -207,6 +213,13 @@ jobs:
mv ./src-tauri/gen/android/app/build/outputs/apk/universal/release/app-universal-release-signed.apk ./src-tauri/gen/android/app/build/outputs/apk/universal/release/ObsidianIRC-${{ needs.collect-version.outputs.current_version}}.apk
mv ./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/app-universal-release-signed.aab ./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/ObsidianIRC-${{ needs.collect-version.outputs.current_version}}.aab

- name: Upload signed AAB artifact for Google Play
uses: actions/upload-artifact@v4
with:
name: signed-aab
path: ./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/ObsidianIRC-${{ needs.collect-version.outputs.current_version }}.aab
retention-days: 1
Comment on lines +216 to +221
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 | 🔴 Critical

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
# Check artifact upload path, rename step, and production download expectations
echo "=== Rename step (lines 206-209 area) ==="
sed -n '205,210p' .github/workflows/publish.yaml

echo ""
echo "=== Artifact upload step (lines 211-216) ==="
sed -n '211,216p' .github/workflows/publish.yaml

echo ""
echo "=== Production job artifact download and usage (around line 433) ==="
sed -n '430,440p' .github/workflows/publish.yaml

Repository: ObsidianIRC/ObsidianIRC

Length of output: 1456


Fix artifact upload path after rename operation.

The AAB file is renamed to ObsidianIRC-{version}.aab in the rename step (lines 206-209), but the upload step (line 215) attempts to upload the original filename app-universal-release-signed.aab, which no longer exists after the rename. This causes the artifact upload to fail.

Update the upload path to reference the renamed file: ./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/ObsidianIRC-${{ needs.collect-version.outputs.current_version}}.aab

Alternatively, if the production job expects the artifact named app-universal-release-signed.aab, exclude the AAB from the rename operation or adjust the production job to reference the renamed artifact.

🤖 Prompt for AI Agents
.github/workflows/publish.yaml lines 211-216: the upload step is still pointing
to the old filename app-universal-release-signed.aab which was renamed earlier
to ObsidianIRC-{version}.aab, so update the upload path to
./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/ObsidianIRC-${{
needs.collect-version.outputs.current_version}}.aab (or alternatively reverse
the rename or adjust downstream jobs to expect the original filename) so the
artifact upload references the actual file produced.


- name: Publish
uses: softprops/action-gh-release@v2
with:
Expand All @@ -221,6 +234,165 @@ jobs:
./src-tauri/gen/android/app/build/outputs/apk/universal/release/ObsidianIRC-${{ needs.collect-version.outputs.current_version}}.apk
./src-tauri/gen/android/app/build/outputs/bundle/universalRelease/ObsidianIRC-${{ needs.collect-version.outputs.current_version}}.aab

publish-android-google-play-internal:
runs-on: ubuntu-latest
needs: [collect-version]
permissions:
contents: write
id-token: write
# Only run on pushes to main branch OR manual workflow dispatch
if: (github.ref_type == 'branch' && github.ref_name == 'main') || github.event_name == 'workflow_dispatch'
steps:
- uses: actions/checkout@v4

- name: Authenticate to Google Cloud
id: auth
uses: google-github-actions/auth@v2
with:
workload_identity_provider: ${{ secrets.GOOGLE_WIF_PROVIDER }}
service_account: ${{ secrets.GOOGLE_WIF_SERVICE_ACCOUNT }}
Comment on lines +248 to +253
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 | 🔴 Critical

Add create_credentials_file: true to generate credentials file.

The auth step correctly includes id: auth, but is missing create_credentials_file: true. Without this, steps.auth.outputs.credentials_file_path (used on line 336) will be empty, causing the Google Play upload to fail.

🔎 Proposed fix
      - name: Authenticate to Google Cloud
        id: auth
        uses: google-github-actions/auth@v2
        with:
+         create_credentials_file: true
          workload_identity_provider: ${{ secrets.GOOGLE_WIF_PROVIDER }}
          service_account: ${{ secrets.GOOGLE_WIF_SERVICE_ACCOUNT }}
🤖 Prompt for AI Agents
In .github/workflows/publish.yaml around lines 242 to 247, the Google Cloud auth
step uses google-github-actions/auth@v2 but omits create_credentials_file: true,
so steps.auth.outputs.credentials_file_path will be empty; add
create_credentials_file: true under the with: block for that step so the action
writes a credentials file and makes credentials_file_path available for later
steps.

token_format: 'access_token'
access_token_scopes: 'https://www.googleapis.com/auth/androidpublisher'

- name: Setup Java
uses: actions/setup-java@v4
with:
distribution: "zulu"
java-version: "22"
cache: "gradle"

- name: Setup Android SDK
uses: android-actions/setup-android@v3

- name: Install NDK
run: sdkmanager "ndk;27.0.11902837"

- name: Setup Node
uses: actions/setup-node@v4
with:
node-version: lts/*
cache: "npm"

- name: Install Rust
uses: dtolnay/rust-toolchain@stable
with:
targets: aarch64-linux-android,armv7-linux-androideabi,i686-linux-android,x86_64-linux-android

- name: Rust cache
uses: swatinem/rust-cache@v2
with:
workspaces: "./src-tauri -> target"
shared-key: "android-builds"

- name: Install dependencies
run: npm install

- name: Create internal version code
id: playstore_version
run: |
# Check if version is manually overridden via workflow_dispatch
if [ -n "${{ inputs.google-playstore-version }}" ]; then
echo "✅ Using manually specified version code: ${{ inputs.google-playstore-version }}"
echo "version_code=${{ inputs.google-playstore-version }}" >> $GITHUB_OUTPUT
exit 0
fi

FALLBACK_VERSION=$((1000000 + ${{ github.run_number }}))
echo "Fallback version code: $FALLBACK_VERSION (1,000,000 + run_number)"
echo "version_code=$FALLBACK_VERSION" >> $GITHUB_OUTPUT

- name: Initialize Android project
run: npm run tauri android init -- --ci
env:
NDK_HOME: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837
ANDROID_NDK_ROOT: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837
ANDROID_NDK: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837

- name: Patch build.gradle.kts to use environment variables
run: |
BUILD_GRADLE="src-tauri/gen/android/app/build.gradle.kts"

# Backup original
cp "$BUILD_GRADLE" "${BUILD_GRADLE}.bak"

# Replace versionCode and versionName lines to use env vars with fallback
sed -i 's/versionCode = tauriProperties.*/versionCode = System.getenv("VERSION_CODE")?.toIntOrNull() ?: tauriProperties.getProperty("tauri.android.versionCode", "1").toInt()/' "$BUILD_GRADLE"
sed -i 's/versionName = tauriProperties.*/versionName = System.getenv("VERSION_NAME") ?: tauriProperties.getProperty("tauri.android.versionName", "1.0")/' "$BUILD_GRADLE"

echo "Patched build.gradle.kts to use environment variables"
grep -A 2 "versionCode =" "$BUILD_GRADLE"

- name: Build Android with custom version
run: npm run tauri android build
env:
NDK_HOME: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837
ANDROID_NDK_ROOT: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837
ANDROID_NDK: ${{ env.ANDROID_HOME }}/ndk/27.0.11902837
VERSION_CODE: ${{ steps.playstore_version.outputs.version_code }}
VERSION_NAME: internal-${{ github.run_number }}

- name: Extract android signing key
run: |
echo "${{ secrets.ANDROID_RELEASE_KEYSTORE }}" > src-tauri/gen/android/release.jks.base64
base64 -d src-tauri/gen/android/release.jks.base64 > src-tauri/gen/android/release.decrypted.jks

- name: Sign AAB
run: |
${{ env.ANDROID_HOME }}/build-tools/34.0.0/apksigner sign \
--min-sdk-version 22 \
--v1-signing-enabled true \
--v2-signing-enabled true \
--ks src-tauri/gen/android/release.decrypted.jks \
--ks-key-alias ${{ secrets.ANDROID_RELEASE_KEY }} \
--ks-pass pass:${{ secrets.ANDROID_RELEASE_PASSWORD }} \
--out src-tauri/gen/android/app/build/outputs/bundle/universalRelease/app-universal-release-signed.aab \
src-tauri/gen/android/app/build/outputs/bundle/universalRelease/app-universal-release.aab

- name: Upload to Google Play - Internal Track
uses: r0adkll/upload-google-play@v1
with:
serviceAccountJson: ${{ steps.auth.outputs.credentials_file_path }}
packageName: com.obsidianirc.dev
releaseFiles: src-tauri/gen/android/app/build/outputs/bundle/universalRelease/app-universal-release-signed.aab
track: internal
status: completed
releaseName: Internal build ${{ github.run_number }}
Comment on lines +351 to +359
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 | 🔴 Critical

🧩 Analysis chain

🌐 Web query:

r0adkll/upload-google-play action GOOGLE_APPLICATION_CREDENTIALS WIF authentication

💡 Result:

Yes — use GitHub OIDC / Workload Identity Federation (WIF) via google-github-actions/auth to create a short‑lived credential file and pass its path (or contents) into r0adkll/upload-google-play.

Minimal example (YAML):

  • Authenticate with WIF and create credentials file:
    • uses: google-github-actions/auth@v3
      id: auth
      with:
      create_credentials_file: true
      workload_identity_provider: projects/123456789/locations/global/workloadIdentityPools/POOL/providers/PROVIDER
      service_account: my-sa@my-project.iam.gserviceaccount.com
  • Use upload-google-play and point to that file:
    • uses: r0adkll/upload-google-play@v1
      with:
      serviceAccountJson: ${{ steps.auth.outputs.credentials_file_path }}

      other inputs: serviceAccountEmail, packageName, apkFile, etc.

Notes

  • The upload-google-play action supports both serviceAccountJson (path to file produced by auth action) and serviceAccountJsonPlainText (raw JSON secret). [1]
  • Use google-github-actions/auth to perform Workload Identity Federation and set create_credentials_file so it outputs credentials_file_path. That output is intended to be passed to other actions or to GOOGLE_APPLICATION_CREDENTIALS. [2]
  • Google WIF docs explain the credential configuration / GOOGLE_APPLICATION_CREDENTIALS usage if you instead need to set environment variables for tools that auto-detect creds. [3]

Sources
[1] r0adkll/upload-google-play README (service account + WIF examples).
[2] google-github-actions/auth documentation (create_credentials_file, outputs.credentials_file_path).
[3] Google Cloud Workload Identity Federation / deployment pipelines docs (GOOGLE_APPLICATION_CREDENTIALS usage).


🌐 Web query:

r0adkll/upload-google-play serviceAccountJson WIF workload identity federation

💡 Result:

Yes — r0adkll/upload-google-play supports using Workload Identity Federation (WIF). Process (concise):

  1. In GCP: create a Workload Identity Pool/Provider and grant the provider the necessary IAM roles on the target service account (roles/iam.workloadIdentityUser and, if you need to mint tokens, roles/iam.serviceAccountTokenCreator). Configure the service account with Play Console access (invite its email in Play Console). [1][3]

  2. In your workflow give the job permission to request an OIDC token:
    permissions:
    id-token: write
    contents: read
    and add a step that uses google-github-actions/auth to exchange the GitHub OIDC token for short‑lived credentials, e.g.:

    • id: auth
      uses: google-github-actions/auth@vX
      with:
      workload_identity_provider: 'projects/PROJECT_NUMBER/locations/global/workloadIdentityPools/POOL/providers/PROVIDER'
      service_account: 'sa@PROJECT.iam.gserviceaccount.com'
      create_credentials_file: 'true'
      That action outputs credentials_file_path. [2]
  3. Pass the generated credentials file path into r0adkll/upload-google-play via serviceAccountJson (the action accepts a file path). Example step:

    • uses: r0adkll/upload-google-play@v1
      with:
      serviceAccountJson: ${{ steps.auth.outputs.credentials_file_path }}
      packageName: com.example.app
      releaseFiles: path/to/app.aab
      Also ensure the service account is invited in Play Console and has required app permissions. [1]

Sources:

  • r0adkll/upload-google-play readme (shows WIF example and serviceAccountJson usage). [1]
  • google-github-actions/auth docs (usage for Workload Identity Federation and credentials_file_path output). [2]
  • GCP Workload Identity Federation overview (IAM guidance). [3]

References:
[1] r0adkll/upload-google-play README.
[2] google-github-actions/auth README (Workload Identity Federation).
[3] Google Cloud IAM — Workload Identity Federation.


🌐 Web query:

r0adkll/upload-google-play GitHub action documentation authentication methods

💡 Result:

Short summary — authentication methods supported by r0adkll/upload-google-play:

  • Service account JSON as a secret (plain text): set input serviceAccountJsonPlainText to the JSON contents (recommended for simple setups). [1]
  • Service account JSON file path: set input serviceAccountJson to a file path (e.g., a credentials file produced by another step). [1]
  • Workload Identity / short-lived creds (recommended by GCP): use google-github-actions/auth to obtain short-lived credentials (it outputs a credentials file path you pass to serviceAccountJson). README shows example using google-github-actions/auth and recommends Workload Identity Federation as more secure. [1][2]

Additional required steps: enable the Android Publisher API, create the GCP service account, and invite that service account in Play Console with app permissions. [1]

Sources: r0adkll/upload-google-play README. [1] google-github-actions/auth README (Workload Identity / service account key details). [2]


Use serviceAccountJson input instead of serviceAccountEmail for proper WIF authentication.

The r0adkll/upload-google-play@v1 action requires explicit credentials via serviceAccountJson (file path) or serviceAccountJsonPlainText (raw JSON). It does not automatically read GOOGLE_APPLICATION_CREDENTIALS. The current usage of serviceAccountEmail alone is insufficient for authentication.

Pass the credentials file path from the google-github-actions/auth step:

with:
  serviceAccountJson: ${{ steps.auth.outputs.credentials_file_path }}
  packageName: com.obsidianirc.dev
  releaseFiles: src-tauri/gen/android/app/build/outputs/bundle/universalRelease/app-universal-release-signed.aab
  track: internal
  status: completed
  releaseName: Internal build ${{ github.run_number }}

Ensure the auth step has create_credentials_file: true and is assigned an id (e.g., id: auth).

🤖 Prompt for AI Agents
.github/workflows/publish.yaml around lines 323 to 332: the upload-google-play
step is using serviceAccountEmail only which is insufficient for WIF
authentication; replace serviceAccountEmail with the action's serviceAccountJson
input and pass the credentials file path produced by the auth step (e.g.,
steps.auth.outputs.credentials_file_path), and ensure the preceding
google-github-actions/auth step has id: auth and create_credentials_file: true
so the credentials file is created and its path can be consumed by the upload
action.


publish-android-google-play-production:
runs-on: ubuntu-latest
needs: [collect-version, publish-android]
permissions:
contents: write
id-token: write
if: github.ref_type == 'tag'
steps:
- uses: actions/checkout@v4

- name: Authenticate to Google Cloud
id: auth
uses: google-github-actions/auth@v2
with:
workload_identity_provider: ${{ secrets.GOOGLE_WIF_PROVIDER }}
service_account: ${{ secrets.GOOGLE_WIF_SERVICE_ACCOUNT }}
Comment on lines +371 to +376
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 | 🔴 Critical

Add create_credentials_file: true to generate credentials file.

Same issue as the internal job: the auth step is missing create_credentials_file: true, which will cause the upload on line 369 to fail.

🔎 Proposed fix
      - name: Authenticate to Google Cloud
        id: auth
        uses: google-github-actions/auth@v2
        with:
+         create_credentials_file: true
          workload_identity_provider: ${{ secrets.GOOGLE_WIF_PROVIDER }}
          service_account: ${{ secrets.GOOGLE_WIF_SERVICE_ACCOUNT }}
🤖 Prompt for AI Agents
In .github/workflows/publish.yaml around lines 353 to 358, the Google auth step
using google-github-actions/auth@v2 is missing the create_credentials_file: true
flag so the subsequent upload (line 369) will fail; add create_credentials_file:
true under the with: block for that step so the action writes a credentials file
(usable via GOOGLE_APPLICATION_CREDENTIALS) before running the upload.

token_format: 'access_token'
access_token_scopes: 'https://www.googleapis.com/auth/androidpublisher'

- name: Download signed AAB artifact
uses: actions/download-artifact@v4
with:
name: signed-aab
path: ./

- name: Upload to Google Play - Production Track
uses: r0adkll/upload-google-play@v1
with:
serviceAccountJson: ${{ steps.auth.outputs.credentials_file_path }}
packageName: com.obsidianirc.dev
releaseFiles: ./ObsidianIRC-${{ needs.collect-version.outputs.current_version }}.aab
track: production
status: completed
releaseName: ObsidianIRC v${{ needs.collect-version.outputs.current_version }}

publish-ios:
runs-on: macos-latest
needs: collect-version
Expand Down
17 changes: 5 additions & 12 deletions package-lock.json

Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.

2 changes: 1 addition & 1 deletion package.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
{
"name": "obsidianirc-client",
"private": true,
"version": "0.2.1",
"version": "0.2.3",
"type": "module",
"homepage": "https://github.com/ObsidianIRC/ObsidianIRC",
"scripts": {
Expand Down
20 changes: 13 additions & 7 deletions src-tauri/gen/android/app/src/main/AndroidManifest.xml
Original file line number Diff line number Diff line change
Expand Up @@ -31,36 +31,42 @@
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https" />
<data android:scheme="http" />
<data android:scheme="irc" />
<data android:host="*" />




</intent-filter>
<intent-filter android:autoVerify="true" >
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https" />
<data android:scheme="http" />
<data android:scheme="ircs" />
<data android:host="obsidianirc.github.io" />


<data android:pathPrefix="/" />

</intent-filter>
<!-- DEEP LINK PLUGIN. AUTO-GENERATED. DO NOT REMOVE. -->
<!-- Custom IRC URL schemes -->
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https" />
<data android:scheme="http" />
<data android:scheme="irc" />
</intent-filter>
<intent-filter>
<action android:name="android.intent.action.VIEW" />
<category android:name="android.intent.category.DEFAULT" />
<category android:name="android.intent.category.BROWSABLE" />
<data android:scheme="https" />
<data android:scheme="http" />
<data android:scheme="ircs" />
</intent-filter>
</activity>
Expand Down