1
- import React from 'react' ;
2
-
1
+ import React , { useState , useEffect } from 'react' ;
2
+ import { View , Text , Button , StyleSheet , ScrollView , ActivityIndicator } from 'react-native' ;
3
3
import { createStackNavigator } from '@react-navigation/stack' ;
4
+ import { PEACH_API_KEY , BISQ_API_KEY , ROBOSATS_API_KEY } from '@env' ;
5
+
6
+ // Define types for offers
7
+ interface Offer {
8
+ id : string ;
9
+ price : number ;
10
+ amount : number ;
11
+ [ key : string ] : any ;
12
+ }
13
+
14
+ interface OffersState {
15
+ peachBitcoin : Offer [ ] ;
16
+ bisq : Offer [ ] ;
17
+ roboSats : Offer [ ] ;
18
+ }
19
+
20
+ // Placeholder API service functions with types
21
+ const apiServices = {
22
+ peachBitcoin : {
23
+ getOffers : async ( ) : Promise < Offer [ ] > => {
24
+ try {
25
+ const response = await fetch ( 'https://api.peachbitcoin.com/offers' , {
26
+ headers : {
27
+ 'Authorization' : `Bearer ${ PEACH_API_KEY } ` ,
28
+ 'Content-Type' : 'application/json'
29
+ }
30
+ } ) ;
31
+ if ( ! response . ok ) throw new Error ( 'PeachBitcoin API request failed' ) ;
32
+ return await response . json ( ) ;
33
+ } catch ( error ) {
34
+ console . error ( 'PeachBitcoin API error:' , error ) ;
35
+ return [ ] ;
36
+ }
37
+ }
38
+ } ,
39
+ bisq : {
40
+ getOffers : async ( ) : Promise < Offer [ ] > => {
41
+ try {
42
+ const response = await fetch ( 'https://api.bisq.network/offers' , {
43
+ headers : {
44
+ 'Authorization' : `Bearer ${ BISQ_API_KEY } ` ,
45
+ 'Content-Type' : 'application/json'
46
+ }
47
+ } ) ;
48
+ if ( ! response . ok ) throw new Error ( 'Bisq API request failed' ) ;
49
+ return await response . json ( ) ;
50
+ } catch ( error ) {
51
+ console . error ( 'Bisq API error:' , error ) ;
52
+ return [ ] ;
53
+ }
54
+ }
55
+ } ,
56
+ roboSats : {
57
+ getOffers : async ( ) : Promise < Offer [ ] > => {
58
+ try {
59
+ const response = await fetch ( 'https://api.robosats.com/offers' , {
60
+ headers : {
61
+ 'Authorization' : `Bearer ${ ROBOSATS_API_KEY } ` ,
62
+ 'Content-Type' : 'application/json'
63
+ }
64
+ } ) ;
65
+ if ( ! response . ok ) throw new Error ( 'RoboSats API request failed' ) ;
66
+ return await response . json ( ) ;
67
+ } catch ( error ) {
68
+ console . error ( 'RoboSats API error:' , error ) ;
69
+ return [ ] ;
70
+ }
71
+ }
72
+ }
73
+ } ;
74
+
75
+ // P2P Trading Screen Component
76
+ const P2PTradingScreen : React . FC = ( ) => {
77
+ const [ offers , setOffers ] = useState < OffersState > ( {
78
+ peachBitcoin : [ ] ,
79
+ bisq : [ ] ,
80
+ roboSats : [ ]
81
+ } ) ;
82
+ const [ loading , setLoading ] = useState < boolean > ( false ) ;
83
+
84
+ const fetchAllOffers = async ( ) : Promise < void > => {
85
+ if ( ! PEACH_API_KEY || ! BISQ_API_KEY || ! ROBOSATS_API_KEY ) {
86
+ console . error ( 'Missing API keys in .env file' ) ;
87
+ return ;
88
+ }
89
+
90
+ setLoading ( true ) ;
91
+ try {
92
+ const [ peachOffers , bisqOffers , roboOffers ] = await Promise . all ( [
93
+ apiServices . peachBitcoin . getOffers ( ) ,
94
+ apiServices . bisq . getOffers ( ) ,
95
+ apiServices . roboSats . getOffers ( )
96
+ ] ) ;
97
+
98
+ setOffers ( {
99
+ peachBitcoin : peachOffers ,
100
+ bisq : bisqOffers ,
101
+ roboSats : roboOffers
102
+ } ) ;
103
+ } catch ( error ) {
104
+ console . error ( 'Error fetching offers:' , error ) ;
105
+ } finally {
106
+ setLoading ( false ) ;
107
+ }
108
+ } ;
109
+
110
+ useEffect ( ( ) => {
111
+ fetchAllOffers ( ) ;
112
+ } , [ ] ) ;
113
+
114
+ interface OfferCardProps {
115
+ platform : string ;
116
+ offer : Offer ;
117
+ }
118
+
119
+ const OfferCard : React . FC < OfferCardProps > = ( { platform, offer } ) => (
120
+ < View style = { styles . offerCard } >
121
+ < Text style = { styles . platform } > { platform } </ Text >
122
+ < Text > Price: { offer . price || 'N/A' } BTC</ Text >
123
+ < Text > Amount: { offer . amount || 'N/A' } </ Text >
124
+ < Button
125
+ title = "Buy Now"
126
+ onPress = { ( ) => console . log ( `Buying from ${ platform } ` , offer ) }
127
+ />
128
+ </ View >
129
+ ) ;
130
+
131
+ return (
132
+ < ScrollView style = { styles . container } >
133
+ < Text style = { styles . header } > P2P Bitcoin Trading</ Text >
134
+
135
+ { loading && < ActivityIndicator size = "large" color = "#0000ff" /> }
136
+
137
+ { /* PeachBitcoin Offers */ }
138
+ < View style = { styles . section } >
139
+ < Text style = { styles . sectionTitle } > PeachBitcoin Offers</ Text >
140
+ { offers . peachBitcoin . map ( ( offer ) => (
141
+ < OfferCard key = { `peach-${ offer . id } ` } platform = "PeachBitcoin" offer = { offer } />
142
+ ) ) }
143
+ </ View >
144
+
145
+ { /* Bisq Offers */ }
146
+ < View style = { styles . section } >
147
+ < Text style = { styles . sectionTitle } > Bisq Offers</ Text >
148
+ { offers . bisq . map ( ( offer ) => (
149
+ < OfferCard key = { `bisq-${ offer . id } ` } platform = "Bisq" offer = { offer } />
150
+ ) ) }
151
+ </ View >
152
+
153
+ { /* RoboSats Offers */ }
154
+ < View style = { styles . section } >
155
+ < Text style = { styles . sectionTitle } > RoboSats Offers</ Text >
156
+ { offers . roboSats . map ( ( offer ) => (
157
+ < OfferCard key = { `robo-${ offer . id } ` } platform = "RoboSats" offer = { offer } />
158
+ ) ) }
159
+ </ View >
160
+
161
+ < Button title = "Refresh Offers" onPress = { fetchAllOffers } />
162
+ </ ScrollView >
163
+ ) ;
164
+ } ;
165
+
166
+ // Styles
167
+ const styles = StyleSheet . create ( {
168
+ container : {
169
+ flex : 1 ,
170
+ padding : 16 ,
171
+ backgroundColor : '#fff'
172
+ } ,
173
+ header : {
174
+ fontSize : 24 ,
175
+ fontWeight : 'bold' as 'bold' ,
176
+ marginBottom : 20 ,
177
+ textAlign : 'center' as 'center'
178
+ } ,
179
+ section : {
180
+ marginBottom : 24
181
+ } ,
182
+ sectionTitle : {
183
+ fontSize : 18 ,
184
+ fontWeight : '600' as '600' ,
185
+ marginBottom : 12
186
+ } ,
187
+ offerCard : {
188
+ padding : 16 ,
189
+ borderWidth : 1 ,
190
+ borderColor : '#ddd' ,
191
+ borderRadius : 8 ,
192
+ marginBottom : 12
193
+ } ,
194
+ platform : {
195
+ fontSize : 16 ,
196
+ fontWeight : '500' as '500' ,
197
+ marginBottom : 8
198
+ }
199
+ } ) ;
200
+
201
+ // Stack Navigator Setup
202
+ const Stack = createStackNavigator ( ) ;
203
+
204
+ const P2PNavigator : React . FC = ( ) => {
205
+ return (
206
+ < Stack . Navigator >
207
+ < Stack . Screen
208
+ name = "P2PTrading"
209
+ component = { P2PTradingScreen }
210
+ options = { { title : 'P2P Bitcoin Trading' } }
211
+ />
212
+ </ Stack . Navigator >
213
+ ) ;
214
+ } ;
4
215
216
+ export default P2PNavigator ;
0 commit comments