@umituz/react-native-subscription 2.14.98 → 2.14.100

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.
Files changed (92) hide show
  1. package/README.md +211 -395
  2. package/package.json +1 -1
  3. package/src/application/README.md +46 -225
  4. package/src/application/ports/README.md +42 -97
  5. package/src/domain/README.md +36 -384
  6. package/src/domain/constants/README.md +0 -56
  7. package/src/domain/entities/README.md +43 -169
  8. package/src/domain/errors/README.md +33 -287
  9. package/src/domain/value-objects/README.md +43 -179
  10. package/src/domains/README.md +52 -0
  11. package/src/domains/README.md.bak +274 -0
  12. package/src/domains/config/README.md +93 -383
  13. package/src/domains/config/domain/README.md +37 -0
  14. package/src/domains/config/domain/entities/README.md +41 -0
  15. package/src/domains/paywall/README.md +99 -369
  16. package/src/domains/paywall/components/README.md +34 -178
  17. package/src/domains/paywall/entities/README.md +34 -193
  18. package/src/domains/paywall/hooks/README.md +34 -122
  19. package/src/domains/wallet/README.md +34 -275
  20. package/src/domains/wallet/README.md.bak +209 -0
  21. package/src/domains/wallet/domain/README.md +34 -101
  22. package/src/domains/wallet/domain/entities/README.md +34 -115
  23. package/src/domains/wallet/domain/errors/README.md +34 -151
  24. package/src/domains/wallet/infrastructure/README.md +34 -89
  25. package/src/domains/wallet/presentation/components/README.md +34 -224
  26. package/src/domains/wallet/presentation/hooks/README.md +34 -248
  27. package/src/infrastructure/README.md +37 -496
  28. package/src/infrastructure/mappers/README.md +0 -13
  29. package/src/infrastructure/repositories/README.md +74 -360
  30. package/src/infrastructure/services/README.md +95 -370
  31. package/src/presentation/README.md +123 -408
  32. package/src/presentation/README.md.bak +172 -0
  33. package/src/presentation/components/README.md +151 -179
  34. package/src/presentation/components/README.md.bak +217 -0
  35. package/src/presentation/components/details/CreditRow.md +65 -310
  36. package/src/presentation/components/details/DetailRow.md +63 -255
  37. package/src/presentation/components/details/PremiumDetailsCard.md +65 -238
  38. package/src/presentation/components/details/PremiumStatusBadge.md +64 -239
  39. package/src/presentation/components/details/README.md +97 -447
  40. package/src/presentation/components/feedback/PaywallFeedbackModal.md +63 -287
  41. package/src/presentation/components/feedback/README.md +97 -445
  42. package/src/presentation/components/paywall/PaywallModal.md +66 -416
  43. package/src/presentation/components/paywall/README.md +50 -186
  44. package/src/presentation/components/sections/README.md +97 -466
  45. package/src/presentation/components/sections/SubscriptionSection.md +92 -244
  46. package/src/presentation/hooks/README.md +154 -741
  47. package/src/presentation/hooks/useAuthAwarePurchase.md +58 -325
  48. package/src/presentation/hooks/useAuthGate.md +61 -375
  49. package/src/presentation/hooks/useAuthSubscriptionSync.md +66 -370
  50. package/src/presentation/hooks/useCreditChecker.md +73 -378
  51. package/src/presentation/hooks/useCredits.md +74 -313
  52. package/src/presentation/hooks/useCredits.md.bak +231 -0
  53. package/src/presentation/hooks/useCreditsGate.md +66 -318
  54. package/src/presentation/hooks/useDeductCredit.md +96 -156
  55. package/src/presentation/hooks/useDevTestCallbacks.md +63 -394
  56. package/src/presentation/hooks/useFeatureGate.md +105 -150
  57. package/src/presentation/hooks/useFeatureGate.md.bak +284 -0
  58. package/src/presentation/hooks/useInitializeCredits.md +64 -430
  59. package/src/presentation/hooks/usePaywall.md +61 -306
  60. package/src/presentation/hooks/usePaywallOperations.md +64 -458
  61. package/src/presentation/hooks/usePaywallVisibility.md +67 -316
  62. package/src/presentation/hooks/usePremium.md +84 -226
  63. package/src/presentation/hooks/usePremiumGate.md +60 -395
  64. package/src/presentation/hooks/usePremiumWithCredits.md +64 -401
  65. package/src/presentation/hooks/useSubscription.md +66 -422
  66. package/src/presentation/hooks/useSubscriptionDetails.md +65 -410
  67. package/src/presentation/hooks/useSubscriptionGate.md +80 -164
  68. package/src/presentation/hooks/useSubscriptionSettingsConfig.md +66 -346
  69. package/src/presentation/hooks/useSubscriptionStatus.md +66 -396
  70. package/src/presentation/hooks/useUserTier.md +63 -328
  71. package/src/presentation/hooks/useUserTierWithRepository.md +64 -424
  72. package/src/presentation/screens/README.md +48 -190
  73. package/src/presentation/types/README.md +0 -16
  74. package/src/presentation/utils/README.md +0 -21
  75. package/src/revenuecat/README.md +99 -518
  76. package/src/revenuecat/application/README.md +43 -0
  77. package/src/revenuecat/application/ports/README.md +41 -0
  78. package/src/revenuecat/domain/README.md +42 -141
  79. package/src/revenuecat/domain/constants/README.md +41 -0
  80. package/src/revenuecat/domain/entities/README.md +42 -0
  81. package/src/revenuecat/domain/errors/README.md +47 -191
  82. package/src/revenuecat/domain/types/README.md +41 -0
  83. package/src/revenuecat/domain/value-objects/README.md +41 -0
  84. package/src/revenuecat/infrastructure/README.md +41 -0
  85. package/src/revenuecat/infrastructure/config/README.md +32 -23
  86. package/src/revenuecat/infrastructure/handlers/README.md +41 -0
  87. package/src/revenuecat/infrastructure/managers/README.md +34 -42
  88. package/src/revenuecat/infrastructure/services/README.md +42 -0
  89. package/src/revenuecat/infrastructure/utils/README.md +41 -0
  90. package/src/revenuecat/presentation/README.md +42 -0
  91. package/src/revenuecat/presentation/hooks/README.md +29 -35
  92. package/src/utils/README.md +38 -525
@@ -2,167 +2,83 @@
2
2
 
3
3
  Subscription-only feature gating with simple, focused API.
4
4
 
5
- ## Import
6
-
7
- ```typescript
8
- import { useSubscriptionGate } from '@umituz/react-native-subscription';
9
- ```
10
-
11
- ## Signature
12
-
13
- ```typescript
14
- function useSubscriptionGate(params: {
15
- hasSubscription: boolean;
16
- onSubscriptionRequired: () => void;
17
- }): {
18
- hasSubscription: boolean;
19
- requireSubscription: (action: () => void | Promise<void>) => boolean;
20
- }
21
- ```
22
-
23
- ## Parameters
24
-
25
- | Parameter | Type | Default | Description |
26
- |-----------|------|---------|-------------|
27
- | `hasSubscription` | `boolean` | **Required** | Whether user has active subscription |
28
- | `onSubscriptionRequired` | `() => void` | **Required** | Callback when subscription is required |
29
-
30
- ## Returns
31
-
32
- | Property | Type | Description |
33
- |----------|------|-------------|
34
- | `hasSubscription` | `boolean` | User has active subscription |
35
- | `requireSubscription` | `(action) => boolean` | Gate action behind subscription |
36
-
37
- ## Basic Usage
38
-
39
- ```typescript
40
- function PremiumFeature() {
41
- const { isPremium } = usePremium();
42
-
43
- const { requireSubscription, hasSubscription } = useSubscriptionGate({
44
- hasSubscription: isPremium,
45
- onSubscriptionRequired: () => {
46
- showPaywall();
47
- },
48
- });
49
-
50
- const handlePremiumAction = () => {
51
- const allowed = requireSubscription(() => {
52
- executePremiumFeature();
53
- });
54
-
55
- if (!allowed) {
56
- console.log('User was shown paywall');
57
- }
58
- };
59
-
60
- return (
61
- <Button
62
- onPress={handlePremiumAction}
63
- title={hasSubscription ? 'Access' : 'Upgrade to Premium'}
64
- />
65
- );
66
- }
67
- ```
68
-
69
- ## Advanced Usage
70
-
71
- ### With Conditional Rendering
72
-
73
- ```typescript
74
- function ConditionalPremiumFeature() {
75
- const { isPremium } = usePremium();
76
-
77
- const { requireSubscription, hasSubscription } = useSubscriptionGate({
78
- hasSubscription: isPremium,
79
- onSubscriptionRequired: () => {
80
- navigation.navigate('Paywall');
81
- },
82
- });
83
-
84
- if (!hasSubscription) {
85
- return (
86
- <View>
87
- <PremiumLockedIcon />
88
- <Text>This feature requires Premium</Text>
89
- <Button
90
- onPress={() => requireSubscription(() => {})}
91
- title="Upgrade Now"
92
- />
93
- </View>
94
- );
95
- }
96
-
97
- return (
98
- <View>
99
- <Text>Premium Content</Text>
100
- <PremiumFeatureComponent />
101
- </View>
102
- );
103
- }
104
- ```
105
-
106
- ### With Async Actions
107
-
108
- ```typescript
109
- function AsyncPremiumFeature() {
110
- const { isPremium } = usePremium();
111
-
112
- const { requireSubscription } = useSubscriptionGate({
113
- hasSubscription: isPremium,
114
- onSubscriptionRequired: () => {
115
- showPaywall({
116
- feature: 'Advanced Analytics',
117
- onSubscribe: () => {
118
- // Action will execute after subscription
119
- },
120
- });
121
- },
122
- });
123
-
124
- const handleExportData = () => {
125
- requireSubscription(async () => {
126
- await exportLargeDataset();
127
- Alert.alert('Success', 'Data exported successfully');
128
- });
129
- };
130
-
131
- return <Button onPress={handleExportData} title="Export Data" />;
132
- }
133
- ```
134
-
135
- ## Best Practices
136
-
137
- 1. **Simple checks** - Keep gating logic straightforward
138
- 2. **Clear messaging** - Tell users what they're missing
139
- 3. **Smooth upgrades** - Make subscription path obvious
140
- 4. **Track access** - Monitor gate triggers for optimization
141
- 5. **Value first** - Show benefits before locking
142
- 6. **Graceful fallbacks** - Show preview or limited version
143
- 7. **Context-aware** - Customize paywall based on feature
144
-
145
- ## Development Logging
146
-
147
- In development mode, the hook logs useful information:
148
-
149
- ```typescript
150
- // User not premium
151
- [useSubscriptionGate] No subscription, showing paywall
152
-
153
- // User has subscription
154
- [useSubscriptionGate] Has subscription, proceeding
155
- ```
156
-
157
- ## Related Hooks
158
-
159
- - **useAuthGate** - Add authentication requirements
160
- - **useCreditsGate** - Credits-based gating
161
- - **useFeatureGate** - Combined auth + subscription + credits
162
- - **usePremiumGate** - Premium feature gating with auth option
163
-
164
- ## See Also
165
-
166
- - [Subscription Gating](../../../docs/SUBSCRIPTION_GATING.md)
167
- - [Paywall Triggers](../screens/README.md#triggers)
168
- - [usePremium](./usePremium.md)
5
+ ## Location
6
+
7
+ **Import Path**: `@umituz/react-native-subscription`
8
+
9
+ **File**: `src/presentation/hooks/useSubscriptionGate.ts`
10
+
11
+ **Type**: Hook
12
+
13
+ ## Strategy
14
+
15
+ ### Subscription Gating Flow
16
+
17
+ 1. **Subscription Check**: Verify if user has active subscription
18
+ 2. **Gate Function**: Provide requireSubscription function for gating
19
+ 3. **Action Wrapping**: Wrap actions behind subscription check
20
+ 4. **Callback Trigger**: Execute callback when subscription is required
21
+ 5. **Boolean Access**: Provide simple hasSubscription boolean for conditional rendering
22
+
23
+ ### Integration Points
24
+
25
+ - **usePremium**: For subscription status check
26
+ - **Paywall Domain**: For subscription upgrade flow
27
+ - **Feature Gates**: For unified feature access control
28
+
29
+ ## Restrictions
30
+
31
+ ### REQUIRED
32
+
33
+ - **Subscription Status**: MUST provide hasSubscription parameter
34
+ - **Callback**: MUST implement onSubscriptionRequired callback
35
+ - **Return Check**: SHOULD check return value from requireSubscription
36
+
37
+ ### PROHIBITED
38
+
39
+ - **NEVER** show protected content without checking hasSubscription
40
+ - **NEVER** use for security decisions without server validation
41
+ - **DO NOT** assume subscription status (always verify)
42
+
43
+ ### CRITICAL SAFETY
44
+
45
+ - **ALWAYS** verify hasSubscription before allowing access
46
+ - **NEVER** trust client-side state for security
47
+ - **MUST** implement proper upgrade flow
48
+ - **ALWAYS** handle both subscribed and non-subscribed states
49
+
50
+ ## AI Agent Guidelines
51
+
52
+ ### When Implementing Subscription Gates
53
+
54
+ 1. **Always** check hasSubscription before showing protected content
55
+ 2. **Always** provide clear upgrade path in callback
56
+ 3. **Always** use requireSubscription for action gating
57
+ 4. **Never** bypass subscription checks
58
+ 5. **Always** test with both subscribed and non-subscribed users
59
+
60
+ ### Integration Checklist
61
+
62
+ - [ ] Import from correct path: `@umituz/react-native-subscription`
63
+ - [ ] Provide hasSubscription from usePremium
64
+ - [ ] Implement onSubscriptionRequired callback
65
+ - [ ] Use requireSubscription for action gating
66
+ - [ ] Check hasSubscription for conditional rendering
67
+ - [ ] Test with subscribed user
68
+ - [ ] Test with non-subscribed user
69
+ - [ ] Verify upgrade flow triggers correctly
70
+
71
+ ### Common Patterns
72
+
73
+ 1. **Action Gating**: Use requireSubscription to wrap actions
74
+ 2. **Conditional Rendering**: Check hasSubscription for UI
75
+ 3. **Button States**: Disable buttons when not subscribed
76
+ 4. **Upgrade Prompts**: Show in callback when not subscribed
77
+
78
+ ## Related Documentation
79
+
80
+ - **usePremium**: Subscription status check
81
+ - **usePremiumGate**: Premium feature gating
82
+ - **useAuthGate**: Auth + subscription gating
83
+ - **useFeatureGate**: Unified feature gating
84
+ - **Paywall Domain**: `src/domains/paywall/README.md`
@@ -2,373 +2,93 @@
2
2
 
3
3
  Returns ready-to-use configuration for subscription settings screens.
4
4
 
5
- ## Import
5
+ ## Location
6
6
 
7
- ```typescript
8
- import {
9
- useSubscriptionSettingsConfig,
10
- type SubscriptionSettingsConfig
11
- } from '@umituz/react-native-subscription';
12
- ```
7
+ **Import Path**: `@umituz/react-native-subscription`
13
8
 
14
- ## Signature
9
+ **File**: `src/presentation/hooks/useSubscriptionSettingsConfig.ts`
15
10
 
16
- ```typescript
17
- function useSubscriptionSettingsConfig(
18
- params: UseSubscriptionSettingsConfigParams
19
- ): SubscriptionSettingsConfig
11
+ **Type**: Hook
20
12
 
21
- interface UseSubscriptionSettingsConfigParams {
22
- userId: string | undefined;
23
- translations: SubscriptionSettingsTranslations;
24
- creditLimit?: number;
25
- upgradePrompt?: UpgradePromptConfig;
26
- }
13
+ ## Strategy
27
14
 
28
- interface SubscriptionSettingsConfig {
29
- enabled: boolean;
30
- settingsItem: SettingsItemConfig;
31
- sectionConfig: SectionConfig;
32
- }
33
- ```
15
+ ### Settings Configuration Generation
34
16
 
35
- ## Parameters
17
+ 1. **Data Aggregation**: Combine subscription, credits, and tier information
18
+ 2. **Status Determination**: Calculate status type (active/expired/free/canceled)
19
+ 3. **Date Formatting**: Format expiration and purchase dates
20
+ 4. **Credit Items**: Generate credit item list with optional limit
21
+ 5. **Translation Support**: Apply provided translations to all strings
22
+ 6. **Upgrade Prompt**: Optional upgrade prompt configuration
36
23
 
37
- | Parameter | Type | Default | Description |
38
- |-----------|------|---------|-------------|
39
- | `userId` | `string \| undefined` | **Required** | User ID |
40
- | `translations` | `SubscriptionSettingsTranslations` | **Required** | Localized strings |
41
- | `creditLimit` | `number` | `undefined` | Max credits to display |
42
- | `upgradePrompt` | `UpgradePromptConfig` | `undefined` | Upgrade prompt configuration |
24
+ ### Integration Points
43
25
 
44
- ## Translations
26
+ - **useSubscriptionStatus**: For subscription status details
27
+ - **useCredits**: For credits information
28
+ - **useUserTier**: For tier determination
29
+ - **Settings UI**: For settings screen integration
30
+ - **Translation System**: For localization support
45
31
 
46
- ```typescript
47
- interface SubscriptionSettingsTranslations {
48
- title: string; // e.g., "Subscription"
49
- description: string; // e.g., "Manage your subscription"
50
- statusLabel: string; // e.g., "Status"
51
- statusActive: string; // e.g., "Active"
52
- statusExpired: string; // e.g., "Expired"
53
- statusFree: string; // e.g., "Free"
54
- statusCanceled: string; // e.g., "Canceled"
55
- expiresLabel: string; // e.g., "Expires on"
56
- purchasedLabel: string; // e.g., "Purchased on"
57
- lifetimeLabel: string; // e.g., "Lifetime"
58
- creditsTitle: string; // e.g., "Credits"
59
- remainingLabel: string; // e.g., "remaining"
60
- manageButton: string; // e.g., "Manage Subscription"
61
- upgradeButton: string; // e.g., "Upgrade to Premium"
62
- }
63
- ```
32
+ ## Restrictions
64
33
 
65
- ## Basic Usage
34
+ ### REQUIRED
66
35
 
67
- ```typescript
68
- function SubscriptionSettings() {
69
- const { user } = useAuth();
36
+ - **User ID**: MUST provide valid userId parameter
37
+ - **Translations**: MUST provide all translation strings
38
+ - **Null Handling**: MUST handle null dates and values
39
+ - **Enabled Check**: MUST check config.enabled before use
70
40
 
71
- const config = useSubscriptionSettingsConfig({
72
- userId: user?.uid,
73
- translations: {
74
- title: 'Subscription',
75
- description: 'Manage your subscription',
76
- statusLabel: 'Status',
77
- statusActive: 'Active',
78
- statusExpired: 'Expired',
79
- statusFree: 'Free',
80
- statusCanceled: 'Canceled',
81
- expiresLabel: 'Expires on',
82
- purchasedLabel: 'Purchased on',
83
- lifetimeLabel: 'Lifetime',
84
- creditsTitle: 'Credits',
85
- remainingLabel: 'remaining',
86
- manageButton: 'Manage Subscription',
87
- upgradeButton: 'Upgrade to Premium',
88
- },
89
- });
41
+ ### PROHIBITED
90
42
 
91
- if (!config.enabled) return null;
43
+ - **NEVER** use without providing all translations
44
+ - **NEVER** assume config is enabled (check enabled flag)
45
+ - **DO NOT** hardcode translation strings
46
+ - **DO NOT** use without userId
92
47
 
93
- return (
94
- <SettingsSection>
95
- <SettingsItem
96
- title={config.settingsItem.title}
97
- description={config.settingsItem.description}
98
- onPress={config.settingsItem.onPress}
99
- icon={config.settingsItem.icon}
100
- />
101
- </SettingsSection>
102
- );
103
- }
104
- ```
48
+ ### CRITICAL SAFETY
105
49
 
106
- ## Advanced Usage
50
+ - **ALWAYS** check config.enabled before rendering
51
+ - **MUST** provide complete translation objects
52
+ - **ALWAYS** handle null dates gracefully
53
+ - **NEVER** trust client-side config for security
107
54
 
108
- ### With Custom Translations
55
+ ## AI Agent Guidelines
109
56
 
110
- ```typescript
111
- function LocalizedSettings() {
112
- const { t } = useTranslation();
113
- const { user } = useAuth();
57
+ ### When Implementing Settings Config
114
58
 
115
- const config = useSubscriptionSettingsConfig({
116
- userId: user?.uid,
117
- translations: {
118
- title: t('subscription.title'),
119
- description: t('subscription.description'),
120
- statusLabel: t('subscription.status_label'),
121
- statusActive: t('subscription.status_active'),
122
- statusExpired: t('subscription.status_expired'),
123
- statusFree: t('subscription.status_free'),
124
- statusCanceled: t('subscription.status_canceled'),
125
- expiresLabel: t('subscription.expires_label'),
126
- purchasedLabel: t('subscription.purchased_label'),
127
- lifetimeLabel: t('subscription.lifetime_label'),
128
- creditsTitle: t('subscription.credits_title'),
129
- remainingLabel: t('subscription.remaining_label'),
130
- manageButton: t('subscription.manage_button'),
131
- upgradeButton: t('subscription.upgrade_button'),
132
- },
133
- });
59
+ 1. **Always** provide complete translations
60
+ 2. **Always** check config.enabled
61
+ 3. **Always** handle null dates
62
+ 4. **Always** format dates appropriately
63
+ 5. **Never** use for security decisions without server validation
134
64
 
135
- return <SubscriptionConfigView config={config} />;
136
- }
137
- ```
65
+ ### Integration Checklist
138
66
 
139
- ### With Credit Limit
67
+ - [ ] Import from correct path: `@umituz/react-native-subscription`
68
+ - [ ] Provide valid userId
69
+ - [ ] Provide complete translations
70
+ - [ ] Check config.enabled
71
+ - [ ] Handle null dates
72
+ - [ ] Format dates appropriately
73
+ - [ ] Apply credit limit if needed
74
+ - [ ] Configure upgrade prompt if needed
75
+ - [ ] Test with active subscription
76
+ - [ ] Test with expired subscription
77
+ - [ ] Test with free user
78
+ - [ ] Test with lifetime subscription
140
79
 
141
- ```typescript
142
- function SettingsWithCreditLimit() {
143
- const { user } = useAuth();
80
+ ### Common Patterns
144
81
 
145
- const config = useSubscriptionSettingsConfig({
146
- userId: user?.uid,
147
- translations: englishTranslations,
148
- creditLimit: 10, // Only show up to 10 credit items
149
- });
82
+ 1. **Settings List Item**: Quick access item in settings
83
+ 2. **Detailed Section**: Comprehensive subscription section
84
+ 3. **Localized Settings**: Use with translation libraries
85
+ 4. **Credit Limit**: Limit displayed credit items
86
+ 5. **Upgrade Prompt**: Show upgrade prompt for free users
150
87
 
151
- return (
152
- <ScrollView>
153
- <SubscriptionSection config={config} />
154
- </ScrollView>
155
- );
156
- }
157
- ```
88
+ ## Related Documentation
158
89
 
159
- ### With Upgrade Prompt
160
-
161
- ```typescript
162
- function SettingsWithUpgradePrompt() {
163
- const { user } = useAuth();
164
-
165
- const config = useSubscriptionSettingsConfig({
166
- userId: user?.uid,
167
- translations: englishTranslations,
168
- upgradePrompt: {
169
- showPrompt: true,
170
- highlightBenefits: [
171
- 'Unlimited access',
172
- 'Priority support',
173
- 'Ad-free experience',
174
- ],
175
- discountOffer: 'Save 50% with annual plan',
176
- },
177
- });
178
-
179
- return (
180
- <View>
181
- <SubscriptionSection config={config} />
182
- {!config.sectionConfig.isPremium && config.sectionConfig.upgradePrompt && (
183
- <UpgradePromptCard prompt={config.sectionConfig.upgradePrompt} />
184
- )}
185
- </View>
186
- );
187
- }
188
- ```
189
-
190
- ### Complete Subscription Settings Screen
191
-
192
- ```typescript
193
- function SubscriptionSettingsScreen() {
194
- const { user } = useAuth();
195
-
196
- const config = useSubscriptionSettingsConfig({
197
- userId: user?.uid,
198
- translations: {
199
- title: 'Subscription',
200
- description: 'Manage your subscription',
201
- statusLabel: 'Status',
202
- statusActive: 'Active',
203
- statusExpired: 'Expired',
204
- statusFree: 'Free',
205
- statusCanceled: 'Canceled',
206
- expiresLabel: 'Expires on',
207
- purchasedLabel: 'Purchased on',
208
- lifetimeLabel: 'Lifetime',
209
- creditsTitle: 'Credits',
210
- remainingLabel: 'remaining',
211
- manageButton: 'Manage Subscription',
212
- upgradeButton: 'Upgrade to Premium',
213
- },
214
- creditLimit: 8,
215
- upgradePrompt: {
216
- showPrompt: true,
217
- highlightBenefits: [
218
- 'Unlimited access to all features',
219
- 'Priority customer support',
220
- 'Ad-free experience',
221
- ],
222
- },
223
- });
224
-
225
- if (!config.enabled) return null;
226
-
227
- const { settingsItem, sectionConfig } = config;
228
-
229
- return (
230
- <ScrollView style={styles.container}>
231
- {/* Settings List Item */}
232
- <SettingsList>
233
- <SettingsListItem
234
- title={settingsItem.title}
235
- description={settingsItem.description}
236
- icon={settingsItem.icon}
237
- onPress={settingsItem.onPress}
238
- badge={settingsItem.statusLabel}
239
- />
240
- </SettingsList>
241
-
242
- {/* Detailed Section */}
243
- <Card style={styles.card}>
244
- <Card.Title>{sectionConfig.translations.title}</Card.Title>
245
-
246
- <View style={styles.section}>
247
- <DetailRow
248
- label={sectionConfig.translations.statusLabel}
249
- value={sectionConfig.statusType === 'active'
250
- ? sectionConfig.translations.statusActive
251
- : sectionConfig.statusType === 'expired'
252
- ? sectionConfig.translations.statusExpired
253
- : sectionConfig.translations.statusFree}
254
- />
255
-
256
- {sectionConfig.expirationDate && (
257
- <DetailRow
258
- label={sectionConfig.translations.expiresLabel}
259
- value={sectionConfig.expirationDate}
260
- />
261
- )}
262
-
263
- {sectionConfig.purchaseDate && (
264
- <DetailRow
265
- label={sectionConfig.translations.purchasedLabel}
266
- value={sectionConfig.purchaseDate}
267
- />
268
- )}
269
-
270
- {sectionConfig.isLifetime && (
271
- <DetailRow
272
- label=""
273
- value={sectionConfig.translations.lifetimeLabel}
274
- />
275
- )}
276
- </View>
277
-
278
- {/* Credits Section */}
279
- {sectionConfig.credits.length > 0 && (
280
- <View style={styles.section}>
281
- <Text style={styles.creditsTitle}>
282
- {sectionConfig.translations.creditsTitle}
283
- </Text>
284
- {sectionConfig.credits.map((credit, index) => (
285
- <View key={index} style={styles.creditItem}>
286
- <Icon name="coin" size={16} />
287
- <Text>{credit.amount}</Text>
288
- <Text>{sectionConfig.translations.remainingLabel}</Text>
289
- </View>
290
- ))}
291
- </View>
292
- )}
293
-
294
- {/* Actions */}
295
- <View style={styles.actions}>
296
- {sectionConfig.onUpgrade && !sectionConfig.isPremium && (
297
- <Button
298
- onPress={sectionConfig.onUpgrade}
299
- title={sectionConfig.translations.upgradeButton}
300
- />
301
- )}
302
-
303
- {sectionConfig.isPremium && (
304
- <Button
305
- onPress={() => Linking.openURL('https://apps.apple.com/account/subscriptions')}
306
- title={sectionConfig.translations.manageButton}
307
- variant="outline"
308
- />
309
- )}
310
- </View>
311
- </Card>
312
- </ScrollView>
313
- );
314
- }
315
- ```
316
-
317
- ## Configuration Object
318
-
319
- ### settingsItem
320
-
321
- Quick access item for settings list:
322
-
323
- ```typescript
324
- interface SettingsItemConfig {
325
- title: string; // "Subscription"
326
- description: string; // "Manage your subscription"
327
- isPremium: boolean; // Premium status
328
- statusLabel: string; // "Active" or "Free"
329
- icon: string; // "diamond"
330
- onPress: () => void; // Open paywall
331
- }
332
- ```
333
-
334
- ### sectionConfig
335
-
336
- Detailed section configuration:
337
-
338
- ```typescript
339
- interface SectionConfig {
340
- statusType: 'active' | 'expired' | 'free' | 'canceled';
341
- isPremium: boolean;
342
- expirationDate: string | null; // "January 15, 2024"
343
- purchaseDate: string | null; // "January 15, 2023"
344
- isLifetime: boolean;
345
- daysRemaining: number | null; // 30
346
- willRenew: boolean;
347
- credits: CreditItem[];
348
- translations: SubscriptionSettingsTranslations;
349
- onUpgrade: () => void;
350
- upgradePrompt?: UpgradePromptConfig;
351
- }
352
- ```
353
-
354
- ## Best Practices
355
-
356
- 1. **Provide all translations** - Ensure all strings are localized
357
- 2. **Handle null values** - Dates may be null for lifetime subs
358
- 3. **Use credit limit** - Limit credit items for better UX
359
- 4. **Customize upgrade prompt** - Tailor to your app's benefits
360
- 5. **Test all states** - Active, expired, free, lifetime
361
- 6. **Handle navigation** - Implement onPress handlers
362
- 7. **Format dates** - Use locale-appropriate formatting
363
-
364
- ## Related Hooks
365
-
366
- - **useSubscriptionStatus** - For subscription status details
367
- - **useCredits** - For credits information
368
- - **useSubscriptionDetails** - For package and pricing info
369
-
370
- ## See Also
371
-
372
- - [Settings Screen](../screens/README.md#settings)
373
- - [Subscription Utilities](../utils/subscriptionDateUtils.md)
374
- - [Config Types](../types/SubscriptionSettingsTypes.md)
90
+ - **useSubscriptionStatus**: For subscription status details
91
+ - **useCredits**: For credits information
92
+ - **useSubscriptionDetails**: For package and pricing info
93
+ - **Settings Screen**: `src/presentation/screens/README.md`
94
+ - **Subscription Utilities**: `src/utils/subscriptionDateUtils.md`