react-native-debug-toolkit 0.1.4 → 0.1.5
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.
|
@@ -0,0 +1,41 @@
|
|
|
1
|
+
---
|
|
2
|
+
description:
|
|
3
|
+
globs:
|
|
4
|
+
alwaysApply: false
|
|
5
|
+
---
|
|
6
|
+
|
|
7
|
+
You are an expert in TypeScript, React Native, Expo, and Mobile App Development.
|
|
8
|
+
|
|
9
|
+
Code Style and Structure:
|
|
10
|
+
- Write concise, type-safe TypeScript code.
|
|
11
|
+
- Use functional components and hooks over class components.
|
|
12
|
+
- Ensure components are modular, reusable, and maintainable.
|
|
13
|
+
- Organize files by feature, grouping related components, hooks, and styles.
|
|
14
|
+
|
|
15
|
+
Naming Conventions:
|
|
16
|
+
- Use camelCase for variable and function names (e.g., `isFetchingData`, `handleUserInput`).
|
|
17
|
+
- Use PascalCase for component names (e.g., `UserProfile`, `ChatScreen`).
|
|
18
|
+
|
|
19
|
+
TypeScript Usage:
|
|
20
|
+
- Use TypeScript for all components, favoring interfaces for props and state.
|
|
21
|
+
- Enable strict typing in `tsconfig.json`.
|
|
22
|
+
- Avoid using `any`; strive for precise types.
|
|
23
|
+
- Utilize `React.FC` for defining functional components with props.
|
|
24
|
+
|
|
25
|
+
Performance Optimization:
|
|
26
|
+
- Minimize `useEffect`, `useState`, and heavy computations inside render methods.
|
|
27
|
+
- Use `React.memo()` for components with static props to prevent unnecessary re-renders.
|
|
28
|
+
- Optimize FlatLists with props like `removeClippedSubviews`, `maxToRenderPerBatch`, and `windowSize`.
|
|
29
|
+
- Use `getItemLayout` for FlatLists when items have a consistent size to improve performance.
|
|
30
|
+
- Avoid anonymous functions in `renderItem` or event handlers to prevent re-renders.
|
|
31
|
+
|
|
32
|
+
UI and Styling:
|
|
33
|
+
- Use consistent styling, either through `StyleSheet.create()` or Styled Components.
|
|
34
|
+
- Ensure responsive design by considering different screen sizes and orientations.
|
|
35
|
+
- Optimize image handling using libraries designed for React Native
|
|
36
|
+
|
|
37
|
+
Best Practices:
|
|
38
|
+
- Follow React Native's threading model to ensure smooth UI performance.
|
|
39
|
+
- Utilize CodePush Build and Updates for continuous deployment and Over-The-Air (OTA) updates.
|
|
40
|
+
- Use React Navigation for handling navigation and deep linking with best practices.
|
|
41
|
+
|
|
@@ -38,15 +38,18 @@ const CollapsibleSection = ({ title, children, initiallyExpanded = false }) => {
|
|
|
38
38
|
|
|
39
39
|
const LongTextContent = ({ text }) => {
|
|
40
40
|
return (
|
|
41
|
-
<
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
{
|
|
48
|
-
|
|
49
|
-
|
|
41
|
+
<View style={styles.longTextWrapper}>
|
|
42
|
+
<ScrollView
|
|
43
|
+
style={styles.longTextContainer}
|
|
44
|
+
contentContainerStyle={styles.longTextContent}
|
|
45
|
+
showsVerticalScrollIndicator={true}
|
|
46
|
+
nestedScrollEnabled={true}
|
|
47
|
+
bounces={false}>
|
|
48
|
+
<Text style={styles.jsonString} selectable={true}>
|
|
49
|
+
{text}
|
|
50
|
+
</Text>
|
|
51
|
+
</ScrollView>
|
|
52
|
+
</View>
|
|
50
53
|
)
|
|
51
54
|
}
|
|
52
55
|
|
|
@@ -283,8 +286,7 @@ const HttpLogDetails = ({ log }) => {
|
|
|
283
286
|
contentContainerStyle={styles.contentContainer}
|
|
284
287
|
showsVerticalScrollIndicator={true}
|
|
285
288
|
scrollEventThrottle={16}
|
|
286
|
-
keyboardShouldPersistTaps='handled'
|
|
287
|
-
nestedScrollEnabled={true}>
|
|
289
|
+
keyboardShouldPersistTaps='handled'>
|
|
288
290
|
<View style={styles.header}>
|
|
289
291
|
<View style={styles.headerInfo}>
|
|
290
292
|
<Text style={styles.url} numberOfLines={2} selectable={true}>
|
|
@@ -299,6 +301,7 @@ const HttpLogDetails = ({ log }) => {
|
|
|
299
301
|
{(request.method || 'GET').toUpperCase()}
|
|
300
302
|
</Text>
|
|
301
303
|
{status && <ApiStatus status={status} success={success} />}
|
|
304
|
+
{duration && <Text style={styles.duration}>(duration:{duration}ms)</Text>}
|
|
302
305
|
</View>
|
|
303
306
|
</View>
|
|
304
307
|
<CopyButton text={request.url || ''} />
|
|
@@ -320,16 +323,28 @@ const HttpLogDetails = ({ log }) => {
|
|
|
320
323
|
}
|
|
321
324
|
/>
|
|
322
325
|
</View>
|
|
323
|
-
<
|
|
324
|
-
<
|
|
325
|
-
|
|
326
|
+
<View style={styles.dataContentWrapper}>
|
|
327
|
+
<ScrollView
|
|
328
|
+
style={styles.dataContent}
|
|
329
|
+
nestedScrollEnabled={true}
|
|
330
|
+
bounces={false}
|
|
331
|
+
showsVerticalScrollIndicator={true}>
|
|
332
|
+
<JSONValue value={requestData} maxExpandLevel={1} />
|
|
333
|
+
</ScrollView>
|
|
334
|
+
</View>
|
|
326
335
|
</View>
|
|
327
336
|
)}
|
|
328
337
|
|
|
329
338
|
<CollapsibleSection title='Headers'>
|
|
330
|
-
<
|
|
331
|
-
<
|
|
332
|
-
|
|
339
|
+
<View style={styles.dataContentWrapper}>
|
|
340
|
+
<ScrollView
|
|
341
|
+
style={styles.dataContent}
|
|
342
|
+
nestedScrollEnabled={true}
|
|
343
|
+
bounces={false}
|
|
344
|
+
showsVerticalScrollIndicator={true}>
|
|
345
|
+
<JSONValue value={request.headers || {}} maxExpandLevel={0} />
|
|
346
|
+
</ScrollView>
|
|
347
|
+
</View>
|
|
333
348
|
</CollapsibleSection>
|
|
334
349
|
</View>
|
|
335
350
|
</CollapsibleSection>
|
|
@@ -338,12 +353,12 @@ const HttpLogDetails = ({ log }) => {
|
|
|
338
353
|
title={`Response ${responseSize}`}
|
|
339
354
|
initiallyExpanded={true}>
|
|
340
355
|
<View style={styles.content}>
|
|
341
|
-
<View style={styles.row}>
|
|
342
|
-
<Text style={styles.label}>Status:{status || (success === false ? 'Error' : 'Unknown')}
|
|
356
|
+
{/* <View style={styles.row}>
|
|
357
|
+
<Text style={styles.label}>Status: {status || (success === false ? 'Error' : 'Unknown')}
|
|
343
358
|
{status && response.statusText ? ` (${response.statusText})` : ''}
|
|
344
|
-
{duration && `
|
|
359
|
+
{duration && ` Duration: (${duration}ms)`}
|
|
345
360
|
</Text>
|
|
346
|
-
</View>
|
|
361
|
+
</View> */}
|
|
347
362
|
|
|
348
363
|
{error && (
|
|
349
364
|
<View style={styles.errorSection}>
|
|
@@ -366,24 +381,28 @@ const HttpLogDetails = ({ log }) => {
|
|
|
366
381
|
}
|
|
367
382
|
/>
|
|
368
383
|
</View>
|
|
384
|
+
<View style={styles.dataContentWrapper}>
|
|
385
|
+
<ScrollView
|
|
386
|
+
style={styles.dataContent}
|
|
387
|
+
nestedScrollEnabled={true}
|
|
388
|
+
bounces={false}
|
|
389
|
+
showsVerticalScrollIndicator={true}>
|
|
390
|
+
<JSONValue value={responseData} maxExpandLevel={1} />
|
|
391
|
+
</ScrollView>
|
|
392
|
+
</View>
|
|
393
|
+
</View>
|
|
394
|
+
)}
|
|
395
|
+
|
|
396
|
+
<CollapsibleSection title='Headers'>
|
|
397
|
+
<View style={styles.dataContentWrapper}>
|
|
369
398
|
<ScrollView
|
|
370
399
|
style={styles.dataContent}
|
|
371
|
-
contentContainerStyle={{ flexGrow: 1 }}
|
|
372
400
|
nestedScrollEnabled={true}
|
|
401
|
+
bounces={false}
|
|
373
402
|
showsVerticalScrollIndicator={true}>
|
|
374
|
-
<JSONValue value={
|
|
403
|
+
<JSONValue value={response.headers || {}} maxExpandLevel={0} />
|
|
375
404
|
</ScrollView>
|
|
376
405
|
</View>
|
|
377
|
-
)}
|
|
378
|
-
|
|
379
|
-
<CollapsibleSection title='Headers'>
|
|
380
|
-
<ScrollView
|
|
381
|
-
style={styles.dataContent}
|
|
382
|
-
contentContainerStyle={{ flexGrow: 1 }}
|
|
383
|
-
nestedScrollEnabled={true}
|
|
384
|
-
showsVerticalScrollIndicator={true}>
|
|
385
|
-
<JSONValue value={response.headers || {}} maxExpandLevel={0} />
|
|
386
|
-
</ScrollView>
|
|
387
406
|
</CollapsibleSection>
|
|
388
407
|
</View>
|
|
389
408
|
</CollapsibleSection>
|
|
@@ -395,10 +414,16 @@ const HttpLogDetails = ({ log }) => {
|
|
|
395
414
|
<Text style={styles.codeBlockLabel}>Debug with cURL</Text>
|
|
396
415
|
<CopyButton text={generateCurl()} />
|
|
397
416
|
</View>
|
|
398
|
-
<View style={styles.
|
|
399
|
-
<
|
|
400
|
-
{
|
|
401
|
-
|
|
417
|
+
<View style={styles.dataContentWrapper}>
|
|
418
|
+
<ScrollView
|
|
419
|
+
style={styles.codeBlock}
|
|
420
|
+
nestedScrollEnabled={true}
|
|
421
|
+
bounces={false}
|
|
422
|
+
showsVerticalScrollIndicator={true}>
|
|
423
|
+
<Text style={styles.codeText} selectable={true}>
|
|
424
|
+
{generateCurl()}
|
|
425
|
+
</Text>
|
|
426
|
+
</ScrollView>
|
|
402
427
|
</View>
|
|
403
428
|
</View>
|
|
404
429
|
</View>
|
|
@@ -559,6 +584,9 @@ const styles = StyleSheet.create({
|
|
|
559
584
|
fontWeight: 'bold',
|
|
560
585
|
color: '#666',
|
|
561
586
|
},
|
|
587
|
+
dataContentWrapper: {
|
|
588
|
+
flex: 1,
|
|
589
|
+
},
|
|
562
590
|
dataContent: {
|
|
563
591
|
flex: 1,
|
|
564
592
|
backgroundColor: '#f8f9fa',
|
|
@@ -582,6 +610,7 @@ const styles = StyleSheet.create({
|
|
|
582
610
|
fontWeight: 'bold',
|
|
583
611
|
},
|
|
584
612
|
codeBlock: {
|
|
613
|
+
flex: 1,
|
|
585
614
|
backgroundColor: '#f8f9fa',
|
|
586
615
|
padding: 10,
|
|
587
616
|
borderRadius: 4,
|
|
@@ -662,9 +691,13 @@ const styles = StyleSheet.create({
|
|
|
662
691
|
color: '#666',
|
|
663
692
|
},
|
|
664
693
|
longTextContainer: {
|
|
665
|
-
|
|
694
|
+
flex: 1,
|
|
666
695
|
paddingHorizontal: 8,
|
|
667
696
|
paddingVertical: 5,
|
|
697
|
+
backgroundColor: '#f8f9fa',
|
|
698
|
+
},
|
|
699
|
+
longTextContent: {
|
|
700
|
+
paddingBottom: 10,
|
|
668
701
|
},
|
|
669
702
|
})
|
|
670
703
|
|
|
@@ -5,7 +5,6 @@ import {
|
|
|
5
5
|
StyleSheet,
|
|
6
6
|
FlatList,
|
|
7
7
|
TouchableOpacity,
|
|
8
|
-
Modal,
|
|
9
8
|
} from 'react-native'
|
|
10
9
|
import HttpLogDetails from './HttpLogDetails'
|
|
11
10
|
|
|
@@ -76,6 +75,44 @@ const SubViewHTTPLogs = ({ logs = [] }) => {
|
|
|
76
75
|
)
|
|
77
76
|
}
|
|
78
77
|
|
|
78
|
+
// If a log is selected, show the details view with a back button
|
|
79
|
+
if (selectedLog) {
|
|
80
|
+
return (
|
|
81
|
+
<View style={styles.container}>
|
|
82
|
+
<View style={styles.detailsHeader}>
|
|
83
|
+
<TouchableOpacity
|
|
84
|
+
style={styles.backButton}
|
|
85
|
+
onPress={() => setSelectedLog(null)}>
|
|
86
|
+
<Text style={styles.backButtonText}>← Back</Text>
|
|
87
|
+
</TouchableOpacity>
|
|
88
|
+
<View style={styles.headerMethodStatus}>
|
|
89
|
+
<Text
|
|
90
|
+
style={[
|
|
91
|
+
styles.headerMethod,
|
|
92
|
+
{ color: getMethodColor(selectedLog.request?.method) },
|
|
93
|
+
]}>
|
|
94
|
+
{(selectedLog.request?.method || 'GET').toUpperCase()}
|
|
95
|
+
</Text>
|
|
96
|
+
<Text
|
|
97
|
+
style={[
|
|
98
|
+
styles.headerStatus,
|
|
99
|
+
{
|
|
100
|
+
color:
|
|
101
|
+
selectedLog.response?.status >= 400
|
|
102
|
+
? '#ff4444'
|
|
103
|
+
: '#00C851',
|
|
104
|
+
},
|
|
105
|
+
]}>
|
|
106
|
+
{selectedLog.response?.status || 'Error'}
|
|
107
|
+
</Text>
|
|
108
|
+
</View>
|
|
109
|
+
</View>
|
|
110
|
+
<HttpLogDetails log={selectedLog} />
|
|
111
|
+
</View>
|
|
112
|
+
)
|
|
113
|
+
}
|
|
114
|
+
|
|
115
|
+
// Otherwise show the list view
|
|
79
116
|
return (
|
|
80
117
|
<View style={styles.container}>
|
|
81
118
|
{logs.length === 0 ? (
|
|
@@ -88,56 +125,6 @@ const SubViewHTTPLogs = ({ logs = [] }) => {
|
|
|
88
125
|
style={styles.list}
|
|
89
126
|
/>
|
|
90
127
|
)}
|
|
91
|
-
|
|
92
|
-
<Modal
|
|
93
|
-
visible={!!selectedLog}
|
|
94
|
-
animationType='slide'
|
|
95
|
-
transparent={true}
|
|
96
|
-
onRequestClose={() => setSelectedLog(null)}>
|
|
97
|
-
{selectedLog && (
|
|
98
|
-
<TouchableOpacity
|
|
99
|
-
style={styles.modalContainer}
|
|
100
|
-
activeOpacity={1}
|
|
101
|
-
onPress={() => setSelectedLog(null)}>
|
|
102
|
-
<TouchableOpacity
|
|
103
|
-
style={styles.modalContent}
|
|
104
|
-
activeOpacity={1}
|
|
105
|
-
onPress={(e) => e.stopPropagation()}>
|
|
106
|
-
<View style={styles.modalHeader}>
|
|
107
|
-
<View style={styles.modalHeaderContent}>
|
|
108
|
-
<View style={styles.modalMethodStatus}>
|
|
109
|
-
<Text
|
|
110
|
-
style={[
|
|
111
|
-
styles.modalMethod,
|
|
112
|
-
{ color: getMethodColor(selectedLog.request?.method) },
|
|
113
|
-
]}>
|
|
114
|
-
{(selectedLog.request?.method || 'GET').toUpperCase()}
|
|
115
|
-
</Text>
|
|
116
|
-
<Text
|
|
117
|
-
style={[
|
|
118
|
-
styles.modalStatus,
|
|
119
|
-
{
|
|
120
|
-
color:
|
|
121
|
-
selectedLog.response?.status >= 400
|
|
122
|
-
? '#ff4444'
|
|
123
|
-
: '#00C851',
|
|
124
|
-
},
|
|
125
|
-
]}>
|
|
126
|
-
{selectedLog.response?.status || 'Error'}
|
|
127
|
-
</Text>
|
|
128
|
-
</View>
|
|
129
|
-
</View>
|
|
130
|
-
<TouchableOpacity
|
|
131
|
-
style={styles.closeButton}
|
|
132
|
-
onPress={() => setSelectedLog(null)}>
|
|
133
|
-
<Text style={styles.closeButtonText}>×</Text>
|
|
134
|
-
</TouchableOpacity>
|
|
135
|
-
</View>
|
|
136
|
-
<HttpLogDetails log={selectedLog} />
|
|
137
|
-
</TouchableOpacity>
|
|
138
|
-
</TouchableOpacity>
|
|
139
|
-
)}
|
|
140
|
-
</Modal>
|
|
141
128
|
</View>
|
|
142
129
|
)
|
|
143
130
|
}
|
|
@@ -211,20 +198,7 @@ const styles = StyleSheet.create({
|
|
|
211
198
|
fontSize: 12,
|
|
212
199
|
marginLeft: 8,
|
|
213
200
|
},
|
|
214
|
-
|
|
215
|
-
flex: 1,
|
|
216
|
-
backgroundColor: 'rgba(0,0,0,0.5)',
|
|
217
|
-
justifyContent: 'flex-end',
|
|
218
|
-
alignItems: 'center',
|
|
219
|
-
},
|
|
220
|
-
modalContent: {
|
|
221
|
-
width: '100%',
|
|
222
|
-
height: '90%',
|
|
223
|
-
backgroundColor: '#fff',
|
|
224
|
-
borderRadius: 10,
|
|
225
|
-
overflow: 'hidden',
|
|
226
|
-
},
|
|
227
|
-
modalHeader: {
|
|
201
|
+
detailsHeader: {
|
|
228
202
|
flexDirection: 'row',
|
|
229
203
|
alignItems: 'center',
|
|
230
204
|
padding: 15,
|
|
@@ -232,36 +206,30 @@ const styles = StyleSheet.create({
|
|
|
232
206
|
borderBottomColor: '#eee',
|
|
233
207
|
backgroundColor: '#f8f9fa',
|
|
234
208
|
},
|
|
235
|
-
|
|
236
|
-
|
|
209
|
+
backButton: {
|
|
210
|
+
paddingHorizontal: 10,
|
|
211
|
+
paddingVertical: 5,
|
|
212
|
+
borderRadius: 4,
|
|
213
|
+
backgroundColor: '#eee',
|
|
237
214
|
marginRight: 10,
|
|
238
215
|
},
|
|
239
|
-
|
|
216
|
+
backButtonText: {
|
|
217
|
+
color: '#333',
|
|
218
|
+
fontWeight: '500',
|
|
219
|
+
},
|
|
220
|
+
headerMethodStatus: {
|
|
240
221
|
flexDirection: 'row',
|
|
241
222
|
alignItems: 'center',
|
|
242
223
|
},
|
|
243
|
-
|
|
224
|
+
headerMethod: {
|
|
244
225
|
fontSize: 16,
|
|
245
226
|
fontWeight: 'bold',
|
|
246
227
|
marginRight: 10,
|
|
247
228
|
},
|
|
248
|
-
|
|
229
|
+
headerStatus: {
|
|
249
230
|
fontSize: 14,
|
|
250
231
|
fontWeight: '600',
|
|
251
232
|
},
|
|
252
|
-
closeButton: {
|
|
253
|
-
width: 30,
|
|
254
|
-
height: 30,
|
|
255
|
-
alignItems: 'center',
|
|
256
|
-
justifyContent: 'center',
|
|
257
|
-
borderRadius: 15,
|
|
258
|
-
backgroundColor: '#eee',
|
|
259
|
-
},
|
|
260
|
-
closeButtonText: {
|
|
261
|
-
fontSize: 20,
|
|
262
|
-
color: '#666',
|
|
263
|
-
lineHeight: 20,
|
|
264
|
-
},
|
|
265
233
|
})
|
|
266
234
|
|
|
267
235
|
export default SubViewHTTPLogs
|
package/package.json
CHANGED