@hot-updater/react-native 0.25.9 → 0.25.11

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -99,7 +99,7 @@ class HotUpdaterImpl {
99
99
  */
100
100
  private fun getIsolationKey(context: Context): String {
101
101
  // Get fingerprint hash directly from resources
102
- val fingerprintId = context.resources.getIdentifier("hot_updater_fingerprint_hash", "string", context.packageName)
102
+ val fingerprintId = StringResourceUtils.getIdentifier(context, "hot_updater_fingerprint_hash")
103
103
  val fingerprintHash =
104
104
  if (fingerprintId != 0) {
105
105
  context.getString(fingerprintId).takeIf { it.isNotEmpty() }
@@ -141,7 +141,7 @@ class HotUpdaterImpl {
141
141
  }
142
142
 
143
143
  fun getChannel(context: Context): String {
144
- val id = context.resources.getIdentifier("hot_updater_channel", "string", context.packageName)
144
+ val id = StringResourceUtils.getIdentifier(context, "hot_updater_channel")
145
145
  return if (id != 0) {
146
146
  context.getString(id).takeIf { it.isNotEmpty() } ?: DEFAULT_CHANNEL
147
147
  } else {
@@ -215,7 +215,7 @@ class HotUpdaterImpl {
215
215
  * @return The fingerprint hash or null if not set
216
216
  */
217
217
  fun getFingerprintHash(context: Context): String? {
218
- val id = context.resources.getIdentifier("hot_updater_fingerprint_hash", "string", context.packageName)
218
+ val id = StringResourceUtils.getIdentifier(context, "hot_updater_fingerprint_hash")
219
219
  return if (id != 0) {
220
220
  context.getString(id).takeIf { it.isNotEmpty() }
221
221
  } else {
@@ -229,7 +229,7 @@ class HotUpdaterImpl {
229
229
  * @return The fingerprint hash or null if not set
230
230
  */
231
231
  fun getFingerprintHash(): String? {
232
- val id = context.resources.getIdentifier("hot_updater_fingerprint_hash", "string", context.packageName)
232
+ val id = StringResourceUtils.getIdentifier(context, "hot_updater_fingerprint_hash")
233
233
  return if (id != 0) {
234
234
  context.getString(id).takeIf { it.isNotEmpty() }
235
235
  } else {
@@ -242,7 +242,7 @@ class HotUpdaterImpl {
242
242
  * @return The channel name or null if not set
243
243
  */
244
244
  fun getChannel(): String {
245
- val id = context.resources.getIdentifier("hot_updater_channel", "string", context.packageName)
245
+ val id = StringResourceUtils.getIdentifier(context, "hot_updater_channel")
246
246
  return if (id != 0) {
247
247
  context.getString(id).takeIf { it.isNotEmpty() } ?: DEFAULT_CHANNEL
248
248
  } else {
@@ -97,12 +97,7 @@ object SignatureVerifier {
97
97
  * @return Public key PEM string or null if not configured
98
98
  */
99
99
  private fun getPublicKeyFromConfig(context: Context): String? {
100
- val resourceId =
101
- context.resources.getIdentifier(
102
- "hot_updater_public_key",
103
- "string",
104
- context.packageName,
105
- )
100
+ val resourceId = StringResourceUtils.getIdentifier(context, "hot_updater_public_key")
106
101
 
107
102
  if (resourceId == 0) {
108
103
  Log.d(TAG, "hot_updater_public_key not found in strings.xml")
@@ -0,0 +1,45 @@
1
+ package com.hotupdater
2
+
3
+ import android.content.Context
4
+
5
+ /**
6
+ * Utility class for string resource lookup operations
7
+ */
8
+ object StringResourceUtils {
9
+ /**
10
+ * Resolves a string resource ID with namespace fallback.
11
+ * Handles AGP 7.0+ where namespace and applicationId are decoupled.
12
+ * @param context Application context
13
+ * @param resourceName The string resource name to resolve
14
+ * @return The resolved resource ID, or 0 if not found
15
+ */
16
+ fun getIdentifier(
17
+ context: Context,
18
+ resourceName: String,
19
+ ): Int {
20
+ var resourceId =
21
+ context.resources.getIdentifier(
22
+ resourceName,
23
+ "string",
24
+ context.packageName,
25
+ )
26
+
27
+ // Fallback: try namespace derived from Application class package
28
+ if (resourceId == 0) {
29
+ val appClassName = context.applicationInfo.className
30
+ if (appClassName != null) {
31
+ val namespace = appClassName.substringBeforeLast('.')
32
+ if (namespace != context.packageName) {
33
+ resourceId =
34
+ context.resources.getIdentifier(
35
+ resourceName,
36
+ "string",
37
+ namespace,
38
+ )
39
+ }
40
+ }
41
+ }
42
+
43
+ return resourceId
44
+ }
45
+ }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@hot-updater/react-native",
3
- "version": "0.25.9",
3
+ "version": "0.25.11",
4
4
  "description": "React Native OTA solution for self-hosted",
5
5
  "main": "lib/commonjs/index",
6
6
  "module": "lib/module/index",
@@ -120,14 +120,14 @@
120
120
  "react-native": "0.79.1",
121
121
  "react-native-builder-bob": "^0.40.10",
122
122
  "typescript": "^5.8.3",
123
- "hot-updater": "0.25.9"
123
+ "hot-updater": "0.25.11"
124
124
  },
125
125
  "dependencies": {
126
126
  "use-sync-external-store": "1.5.0",
127
- "@hot-updater/core": "0.25.9",
128
- "@hot-updater/js": "0.25.9",
129
- "@hot-updater/plugin-core": "0.25.9",
130
- "@hot-updater/cli-tools": "0.25.9"
127
+ "@hot-updater/cli-tools": "0.25.11",
128
+ "@hot-updater/core": "0.25.11",
129
+ "@hot-updater/js": "0.25.11",
130
+ "@hot-updater/plugin-core": "0.25.11"
131
131
  },
132
132
  "scripts": {
133
133
  "build": "bob build && tsc -p plugin/tsconfig.build.json",