Wallet OK

This commit is contained in:
Brice Zele 2020-05-01 23:36:24 +01:00
parent f324f825ee
commit 3cab657336
22 changed files with 1637 additions and 938 deletions

File diff suppressed because one or more lines are too long

View File

@ -23,4 +23,6 @@ export const Color = {
yellowColor: '#FDC60A',
textColor: '#212121',
borderColor: '#c7c7cc',
redColor: 'red',
greenColor: 'green'
}

View File

@ -37,6 +37,7 @@
"react-native-credit-card-input": "^0.4.1",
"react-native-db-models": "^0.1.3",
"react-native-device-info": "^2.1.1",
"react-native-dialog": "^5.6.0",
"react-native-elements": "^1.1.0",
"react-native-geolocation": "^1.0.0",
"react-native-geolocation-service": "4.0.0",
@ -59,6 +60,7 @@
"react-native-range-datepicker": "^1.8.2",
"react-native-reanimated": "^1.0.1",
"react-native-responsive-dimensions": "^2.0.1",
"react-native-root-toast": "^3.2.1",
"react-native-screens": "^2.3.0",
"react-native-simple-dialogs": "1.2.1",
"react-native-snackbar-component": "1.1.8",

View File

@ -0,0 +1,19 @@
import { TREAT_CREDIT_CANCEL_PENDING, TREAT_CREDIT_CANCEL_SUCCESS, TREAT_CREDIT_CANCEL_ERROR, TREAT_CREDIT_CANCEL_RESET } from "../types/CreditManageType";
export const fetchTreatCreditCancelPending = () => ({
type: TREAT_CREDIT_CANCEL_PENDING
});
export const fetchTreatCreditCancelSucsess = (res) => ({
type: TREAT_CREDIT_CANCEL_SUCCESS,
result: res,
});
export const fetchTreatCreditCancelError = (error) => ({
type: TREAT_CREDIT_CANCEL_ERROR,
result: error
});
export const fetchTreatCreditCancelReset = () => ({
type: TREAT_CREDIT_CANCEL_RESET
});

View File

@ -0,0 +1,19 @@
import { TREAT_CREDIT_DEMAND_PENDING, TREAT_CREDIT_DEMAND_SUCCESS, TREAT_CREDIT_DEMAND_ERROR, TREAT_CREDIT_DEMAND_RESET } from "../types/CreditManageType";
export const fetchTreatCreditDemandPending = () => ({
type: TREAT_CREDIT_DEMAND_PENDING
});
export const fetchTreatCreditDemandSucsess = (res) => ({
type: TREAT_CREDIT_DEMAND_SUCCESS,
result: res,
});
export const fetchTreatCreditDemandError = (error) => ({
type: TREAT_CREDIT_DEMAND_ERROR,
result: error
});
export const fetchTreatCreditDemandReset = () => ({
type: TREAT_CREDIT_DEMAND_RESET
});

View File

@ -0,0 +1,35 @@
import { TREAT_CREDIT_CANCEL_PENDING, TREAT_CREDIT_CANCEL_SUCCESS, TREAT_CREDIT_CANCEL_ERROR, TREAT_CREDIT_CANCEL_RESET } from "../types/CreditManageType";
const initialState = {
loadingCancelDemand: false,
resultCancelDemand: null,
errorCancelDemand: null,
};
export default (state = initialState, action) => {
switch (action.type) {
case TREAT_CREDIT_CANCEL_PENDING: return {
...state,
loadingCancelDemand: true
}
case TREAT_CREDIT_CANCEL_SUCCESS: return {
...state,
loadingCancelDemand: false,
resultCancelDemand: action.result.data,
errorCancelDemand: null
}
case TREAT_CREDIT_CANCEL_ERROR: return {
...state,
loadingCancelDemand: false,
resultCancelDemand: null,
errorCancelDemand: action.result
}
case TREAT_CREDIT_CANCEL_RESET: return initialState;
default: {
return state;
}
}
};

View File

@ -0,0 +1,35 @@
import { TREAT_CREDIT_DEMAND_PENDING, TREAT_CREDIT_DEMAND_RESET, TREAT_CREDIT_DEMAND_SUCCESS, TREAT_CREDIT_DEMAND_ERROR } from "../types/CreditManageType";
const initialState = {
loadingTreatDemand: false,
resultTreatDemand: null,
errorTreatDemand: null,
};
export default (state = initialState, action) => {
switch (action.type) {
case TREAT_CREDIT_DEMAND_PENDING: return {
...state,
loadingTreatDemand: true
}
case TREAT_CREDIT_DEMAND_SUCCESS: return {
...state,
loadingTreatDemand: false,
resultTreatDemand: action.result.data,
errorTreatDemand: null
}
case TREAT_CREDIT_DEMAND_ERROR: return {
...state,
loadingTreatDemand: false,
resultTreatDemand: null,
errorTreatDemand: action.result
}
case TREAT_CREDIT_DEMAND_RESET: return initialState;
default: {
return state;
}
}
};

View File

@ -2,6 +2,8 @@ import { combineReducers } from "redux";
import walletReducer from "./WalletReducer";
import authKeyReducer from "./AuthKeyReducer";
import depositReducer from "./DepositReducer";
import creditTreatDemandReducer from "./CreditTreatDemandReducer";
import creditCancelDemandReducer from "./CreditCancelDemandReducer";
import walletHistoryReducer from "./WalletTransactionHistoryReducer";
import walletTransferCommissionReducer from "./WalletTransferCommission";
import { persistCombineReducers } from "redux-persist";
@ -19,7 +21,9 @@ const rootReducer = persistCombineReducers(persistConfig, {
authKeyReducer: authKeyReducer,
depositReducer: depositReducer,
walletHistoryReducer: walletHistoryReducer,
walletTransferCommissionReducer: walletTransferCommissionReducer
walletTransferCommissionReducer: walletTransferCommissionReducer,
creditTreatDemandReducer: creditTreatDemandReducer,
creditCancelDemandReducer: creditCancelDemandReducer
});
export default rootReducer;

View File

@ -0,0 +1,9 @@
export const TREAT_CREDIT_DEMAND_PENDING = 'TREAT_CREDIT_DEMAND_PENDING';
export const TREAT_CREDIT_DEMAND_SUCCESS = 'TREAT_CREDIT_DEMAND_SUCCESS';
export const TREAT_CREDIT_DEMAND_ERROR = 'TREAT_CREDIT_DEMAND_ERROR';
export const TREAT_CREDIT_DEMAND_RESET = 'TREAT_CREDIT_DEMAND_RESET';
export const TREAT_CREDIT_CANCEL_PENDING = 'TREAT_CREDIT_CANCEL_PENDING';
export const TREAT_CREDIT_CANCEL_SUCCESS = 'TREAT_CREDIT_CANCEL_SUCCESS';
export const TREAT_CREDIT_CANCEL_ERROR = 'TREAT_CREDIT_CANCEL_ERROR';
export const TREAT_CREDIT_CANCEL_RESET = 'TREAT_CREDIT_CANCEL_RESET';

View File

@ -17,6 +17,7 @@ import 'moment/locale/en-il'
import 'moment/locale/en-nz'
import DeviceInfo from 'react-native-device-info'
import { Color } from '../../config/Color';
let route = require('./../../route.json');
var theme = require('./../../utils/theme.json');
@ -26,7 +27,25 @@ export class HistoryItem extends React.Component {
constructor(props) {
super(props);
this.state = this.initState();
console.log("HISTORY ITEM PROPS", this.props);
}
statusLabel = (status) => {
switch (status) {
case '0': return I18n.t('NO_TREAT');
case '1': return I18n.t('TREAT');
case '2': return I18n.t('REFUSED');
}
}
colorLabel = (status) => {
switch (status) {
case '0': return Color.accentColor;
case '1': return Color.greenColor;
case '2': return Color.redColor;
}
}
initState() {
var textTitle = ' Transaction ' + this.props.selfData.id;
var textDescription = I18n.t('PHONE') + ' ' + this.props.selfData.phone + " " + I18n.t('DEMAND_TEXT_FIRST_PART') + ' ' + (this.props.selfData.montant) + ' ' + I18n.t('TO_') + ' ';
@ -41,19 +60,21 @@ export class HistoryItem extends React.Component {
return {
title: textTitle,
description: textDescription,
status: this.props.selfData.status === '1' ? I18n.t('TREAT') : I18n.t('NO_TREAT'),
status: this.statusLabel(this.props.selfData.status),
time: re.fromNow(),
navigator: this.props.navigator,
type: t,
colorstate: t === '1' ? 'green' : 'red'
colorstate: this.colorLabel(t)
}
};
render() {
return (
<TouchableOpacity onPress={() =>
this.props.navigator.navigate(route.historyItemDetails,
{ item: this.props.selfData }
this.props.navigator.navigate(route.historyItemDetails, {
item: this.props.selfData,
onGoBack: () => this.props.refresh(),
}
)}>
<View style={style.content}>
@ -163,8 +184,10 @@ export class HistoryListItem extends React.Component {
};
_renderItem = ({ item }) => (
<HistoryItem
refresh={this.props.refresh}
navigator={this.props.navigator}
selfData={item}
refresh={this.props.refresh}
/>
);
constructor(props) {

View File

@ -1,5 +1,5 @@
import React, { Component } from 'react'
import { StyleSheet, View, Text } from 'react-native'
import { StyleSheet, View, Text, Alert, Platform } from 'react-native'
import CardView from 'react-native-cardview'
import Button from 'apsl-react-native-button'
import { responsiveHeight, responsiveWidth } from 'react-native-responsive-dimensions'
@ -9,13 +9,21 @@ import { readUser } from "../../webservice/AuthApi";
let typesta = 0
let moment = require('moment-timezone')
var colorback = 'white'
import I18n from "react-native-i18n"
import I18n from "react-native-i18n";
import { treatCreditDemand, creditDemandResetReducer } from '../../webservice/CreditTreatDemandApi';
import { treatCancelDemand, creditCancelResetReducer } from '../../webservice/CreditCancelDemandeApi';
import { getAgentNetworksList } from "../../webservice/NetworkApi";
import Icon from "./History";
import { Header } from "react-native-elements";
let theme = require('./../../utils/theme.json')
const route = require("./../../route.json")
export default class HistoryItemDetails extends Component {
let theme = require('./../../utils/theme.json');
import { connect } from 'react-redux';
import { bindActionCreators } from 'redux';
import Toast from 'react-native-root-toast';
import { Color } from '../../config/Color'
const route = require("./../../route.json");
import Dialog from "react-native-dialog";
import { FontWeight } from '../../config/typography'
class HistoryItemDetails extends Component {
static navigatorStyle = {
navBarBackgroundColor: theme.accentLight,
@ -38,17 +46,29 @@ export default class HistoryItemDetails extends Component {
typesta = 1
colorback = '#AEAEAE'
sta = I18n.t('TREAT_DEMAND')
} else {
} else if (this.item.status === '0') {
colorback = 'green'
typesta = 2
sta = I18n.t('ACTION_TREAT_DEMAND')
sta = I18n.t('ACCEPTER_DEMANDE')
}
else {
colorback = '#AEAEAE'
typesta = 2
sta = I18n.t('REFUSED')
}
this.state = {
displayAmountModifyDialog: false,
statut: sta,
user: null,
networks: [],
loadingTreat: false,
loadingCancel: false,
triggerTreatmentClick: false,
triggerCancelClick: false,
color: colorback,
montant: null,
isBtnModifyAmountEnabled: false
}
readUser().then(async (user) => {
let networks = []
@ -58,14 +78,298 @@ export default class HistoryItemDetails extends Component {
})
}
render() {
isNormalInteger = (str) => {
return (/[ `!@#$%^&*()_+\-=\[\]{};':"\\|,.<>\/?~]/.test(str)) ? false : true;
}
isMontantValid = () => {
const { montant } = this.state;
if ((parseInt(montant) == 0 || montant < 0))
return false;
else if (!this.isNormalInteger(montant))
return false;
else if (parseInt(montant) > parseInt(this.item.montant))
return false;
else
return true;
}
displayToast = (message) => {
Toast.show(message, {
duration: Toast.durations.SHORT,
position: Toast.positions.BOTTOM,
backgroundColor: Color.primaryColor,
shadow: true,
animation: true,
hideOnPress: true,
delay: 0,
onShow: () => {
// calls on toast\`s appear animation start
},
onShown: () => {
// calls on toast\`s appear animation end.
},
onHide: () => {
// calls on toast\`s hide animation start.
},
onHidden: () => {
// calls on toast\`s hide animation end.
}
});
}
onTreatDemand() {
if (this.item !== "1") {
this.props.creditDemandResetReducer();
this.props.treatCreditDemand(this.item.id);
/* updateCreditDemand(this.item.phone, this.item.id).then((data) => {
this.setState({ loadingTreat: false })
console.log(data);
if (data.success === 1) {
this.setState({ statut: I18n.t('TREAT_DEMAND'), color: "#AEAEAE" })
} else {
console.log(data);
}
}) */
}
}
onCancelDemand = () => {
if (this.item !== "1") {
this.props.treatCancelDemand(this.item.id);
}
}
renderPromptModifyAmountToSend = () => {
return (
<Dialog.Container useNativeDriver={true} visible={this.state.displayAmountModifyDialog}>
<Dialog.Title>{I18n.t('MODIFY_AMOUNT')}</Dialog.Title>
<Dialog.Description style={[FontWeight.bold]}>
{I18n.t('ENTER_NEW_AMOUNT_TO_SEND')}
</Dialog.Description>
<Dialog.Input style={styles.inputAmountText}
value={this.state.montant}
keyboardType="numeric"
onChangeText={(montant) => {
this.setState({ montant }, () => {
if (this.isMontantValid(montant)) {
this.setState({
isBtnModifyAmountEnabled: true
})
}
else
this.setState({
isBtnModifyAmountEnabled: false
});
console.log("this.isMontantValid().isValid", this.isMontantValid());
console.log("isBtnModifyAmountEnabled", this.state.isBtnModifyAmountEnabled);
});
}} />
<Dialog.Button bold={true} label={I18n.t('CANCEL_LABEL')} onPress={() => this.setState({ displayAmountModifyDialog: false })} />
<Dialog.Button bold={true} label={I18n.t('SEND')} disable={this.state.isBtnModifyAmountEnabled} onPress={() => {
this.props.creditDemandResetReducer();
this.props.treatCreditDemand(this.item.id, this.state.montant);
}} />
</Dialog.Container>
)
}
renderAlertErrorTreatOrCancelDemand = () => {
const { errorTreatDemand, resultTreatDemand, resultCancelDemand, errorCancelDemand } = this.props;
if (errorTreatDemand !== null) {
if (typeof errorTreatDemand.data !== 'undefined') {
Alert.alert(
I18n.t("ERROR_TREATMENT_DEMAND"),
errorTreatDemand.data.error,
[{
text: I18n.t('CANCEL_LABEL'),
onPress: () => { },
style: 'cancel'
},
{
text: I18n.t("OK"), onPress: () => {
setTimeout(() => {
this.setState({
displayAmountModifyDialog: true
});
}, 10);
this.props.creditDemandResetReducer();
this.props.creditCancelResetReducer();
}
}
],
{ cancelable: false }
)
}
}
if (errorCancelDemand !== null) {
if (typeof errorCancelDemand.data !== 'undefined') {
Alert.alert(
I18n.t("ERROR_TREATMENT_DEMAND"),
errorCancelDemand.data.error,
[
{
text: I18n.t("OK"), onPress: () => {
this.props.creditCancelResetReducer();
this.props.creditDemandResetReducer();
}
}
],
{ cancelable: false }
)
}
}
if (resultTreatDemand !== null) {
console.log("resultTreatDemand", resultTreatDemand);
if (resultTreatDemand.status === 200) {
this.displayToast(resultTreatDemand.response);
this.props.navigation.goBack();
this.props.navigation.state.params.onGoBack();
}
}
if (resultCancelDemand !== null) {
console.log("resultCancelDemand", resultCancelDemand);
if (resultCancelDemand.status === 200) {
this.displayToast(resultCancelDemand.response);
this.props.navigation.goBack();
this.props.navigation.state.params.onGoBack();
}
}
}
renderBtn() {
const { user } = this.state
console.warn("ITEM ITEM", this.item);
if (user) {
if (this.item.code_parrain === user.code_membre) {
if (this.item.status === '1') {
return (<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: this.state.color
}}
isLoading={this.props.loadingTreatDemand}
onPress={() => {
}}
disabled={true}
textStyle={styles.textbtnstyle}
>
{this.state.statut}
</Button>
)
}
else if (this.item.status === '2') {
return (<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: this.state.color
}}
onPress={() => {
}}
disabled={true}
textStyle={styles.textbtnstyle}
>
{this.state.statut}
</Button>
)
}
else {
return (<View style={{
flexDirection: 'row',
paddingTop: 10
}}>
<View style={{
flex: 1,
alignItems: 'center'
}}>
<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: this.state.color
}}
isLoading={this.props.loadingTreatDemand}
onPress={() => {
this.setState({
triggerTreatmentClick: true
});
this.onTreatDemand()
}}
textStyle={styles.textbtnstyle}
>
{this.state.statut}
</Button>
</View>
<View style={{
flex: 1,
alignItems: 'center'
}}>
<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: Color.redColor
}}
isLoading={this.props.loadingCancelDemand}
onPress={() => {
this.setState({
triggerCancelClick: true
});
this.onCancelDemand();
}}
textStyle={styles.textbtnstyle}
>
{I18n.t('REFUSER_DEMANDE')}
</Button>
</View>
</View>)
}
}
}
}
render() {
console.log("CREDIT MANAGE PROPS", this.props);
let ago = moment.tz(this.item.date_creation, 'Etc/GMT+0').format();
ago = moment(ago)
return (
<View style={this.styles.container}>
<View style={styles.container}>
{this.renderPromptModifyAmountToSend()}
{(this.state.triggerTreatmentClick || this.state.triggerCancelClick) && this.renderAlertErrorTreatOrCancelDemand()}
<CardView
style={this.styles.cardcontainer1}
style={styles.cardcontainer1}
><Text style={{
fontSize: 17,
fontWeight: 'bold',
@ -83,7 +387,7 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{this.item.phone}</Text>
<Text style={styles.simpleuser}>{this.item.phone}</Text>
</View>
<View style={{
flexDirection: 'row',
@ -96,11 +400,11 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{this.item.code_membre}</Text>
<Text style={styles.simpleuser}>{this.item.code_membre}</Text>
</View>
</CardView>
<CardView
style={this.styles.cardcontainer}
style={styles.cardcontainer}
>
<Text style={{
fontSize: 17,
@ -119,7 +423,7 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{this.item.code_parrain}</Text>
<Text style={styles.simpleuser}>{this.item.code_parrain}</Text>
</View>
<View style={{
flexDirection: 'row',
@ -132,7 +436,7 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{this.item.reseau}</Text>
<Text style={styles.simpleuser}>{this.item.reseau}</Text>
</View>
<View style={{
flexDirection: 'row',
@ -145,7 +449,7 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{this.item.montant}</Text>
<Text style={styles.simpleuser}>{this.item.montant}</Text>
</View>
<View style={{
flexDirection: 'row',
@ -158,7 +462,7 @@ export default class HistoryItemDetails extends Component {
marginLeft: 20
}}
/>
<Text style={this.styles.simpleuser}>{ago.format(" Do MMMM YYYY à HH:mm")}</Text>
<Text style={styles.simpleuser}>{ago.format(" Do MMMM YYYY à HH:mm")}</Text>
</View>
<View style={{
flexDirection: 'row',
@ -181,13 +485,46 @@ export default class HistoryItemDetails extends Component {
{this.state.user ? this.renderBtn() : null}
</View>)
}
styles = StyleSheet.create({
}
const mapStateToProps = state => ({
loadingTreatDemand: state.creditTreatDemandReducer.loadingTreatDemand,
resultTreatDemand: state.creditTreatDemandReducer.resultTreatDemand,
errorTreatDemand: state.creditTreatDemandReducer.errorTreatDemand,
loadingCancelDemand: state.creditCancelDemandReducer.loadingCancelDemand,
resultCancelDemand: state.creditCancelDemandReducer.resultCancelDemand,
errorCancelDemand: state.creditCancelDemandReducer.errorCancelDemand
});
const mapDispatchToProps = dispatch => bindActionCreators({
treatCreditDemand: treatCreditDemand,
creditDemandResetReducer: creditDemandResetReducer,
treatCancelDemand: treatCancelDemand,
creditCancelResetReducer: creditCancelResetReducer
}, dispatch);
export default connect(mapStateToProps, mapDispatchToProps)(HistoryItemDetails);
const styles = StyleSheet.create({
container: {
flex: 1,
},
btnstyle: {
},
inputAmountText: {
...Platform.select({
android: {
borderBottomColor: Color.borderColor,
borderBottomWidth: 0.5,
}
})
},
simpleuser: {
marginLeft: responsiveWidth(2),
fontSize: 16,
@ -212,99 +549,3 @@ export default class HistoryItemDetails extends Component {
margin: 3,
}
})
onTreatDemand() {
if (this.item !== "1") {
this.setState({ loadingTreat: true })
console.warn(this.item);
updateCreditDemand(this.item.phone, this.item.id).then((data) => {
this.setState({ loadingTreat: false })
console.log(data);
if (data.success === 1) {
this.setState({ statut: I18n.t('TREAT_DEMAND'), color: "#AEAEAE" })
} else {
console.log(data);
}
})
}
}
renderBtn() {
const { user } = this.state
console.warn("ITEM ITEM", this.item);
if (user) {
if (this.item.code_parrain === user.code_membre) {
if (this.item.status === '1') {
return (<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: this.state.color
}}
isLoading={this.state.loadingTreat}
onPress={() => {
this.onTreatDemand()
}}
textStyle={this.styles.textbtnstyle}
>
{this.state.statut}
</Button>
)
} else {
return (<View style={{
flexDirection: 'row',
paddingTop: 10
}}>
<View style={{
flex: 1,
alignItems: 'center'
}}>
<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: this.state.color
}}
isLoading={this.state.loadingTreat}
onPress={() => {
this.onTreatDemand()
}}
textStyle={this.styles.textbtnstyle}
>
{this.state.statut}
</Button>
</View>
<View style={{
flex: 1,
alignItems: 'center'
}}>
<Button
style={{
borderColor: 'transparent',
borderRadius: 6,
marginLeft: 5,
marginRight: 5,
backgroundColor: '#ccc'
}}
isLoading={this.state.loadingTreat}
onPress={() => {
this.props.navigation.pop();
}}
textStyle={this.styles.textbtnstyle}
>
{I18n.t('QUIT')}
</Button>
</View>
</View>)
}
}
}
}
}

View File

@ -312,6 +312,7 @@ class MyHistory extends React.Component {
return (<HistoryListItem
list={list}
refreshing={() => { this.refreshData() }}
refresh={() => this.refreshData()}
isRefreshing={this.state.isRefreshing}
navigator={this.props.navigation}
style={styles.listbackground} />)
@ -512,7 +513,7 @@ class MyHistory extends React.Component {
if (data.length > 0) {
return (<HistoryItemSectionned
list={list}
navigator={this.props.navigator}
refresh={() => this.refreshData()}
style={styles.listbackground} />)
} else if (this.state.filter) {
@ -678,6 +679,7 @@ class MyHistory extends React.Component {
_renderListDemandsSend() {
console.log("REQUEST DATA", this.state.listdataSend);
return (<View style={styles.container}>
{
this.state.isLoaded ?
@ -748,6 +750,7 @@ class MyHistory extends React.Component {
if (autoref)
this.setState({ isRefreshing: true })
loadDemandeCredit().then((data) => {
if (data.success !== undefined) {
this.setState({ listdata: [] })
this.updateList(data.demands);
@ -757,6 +760,7 @@ class MyHistory extends React.Component {
}).catch((e) => {
console.warn(e)
});
loadMyDemandeCredit().then((data) => {
if (data.success !== undefined) {
this.setState({ listdataSend: [] })

View File

@ -14,7 +14,8 @@ import { IlinkEmitter } from "../../utils/events";
import { CreditCardInput } from "react-native-credit-card-input";
import { Typography, FontWeight } from '../../config/typography';
import depositAction from '../../webservice/DepositApi';
import Dialog, { DialogContent, DialogTitle, DialogFooter, DialogButton } from 'react-native-popup-dialog';
import Dialog from "react-native-dialog";
//import Dialog, { DialogContent, DialogTitle, DialogFooter, DialogButton } from 'react-native-popup-dialog';
let moment = require('moment-timezone');
import 'moment/locale/fr'
import 'moment/locale/es-us'
@ -146,7 +147,66 @@ class WalletDepot extends Component {
return (
<Dialog
<Dialog.Container useNativeDriver={true} visible={this.state.isModalConfirmVisible}>
<Dialog.Title>{I18n.t('CONFIRM_DEPOSIT')}</Dialog.Title>
<View>
<View style={[styles.blockView, { borderBottomColor: Color.borderColor }]}>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text style={[style.body2]}>{I18n.t('AMOUNT')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.state.montant}</Text>
</View>
</View>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text tyle={[Typography.body2]}>{I18n.t('COMMISSION_FEES')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.commissionsFees(this.state.montant, taux_com_client_depot, frais_min_banque_depot)}</Text>
</View>
</View>
</View>
<View style={{ paddingVertical: 10 }}>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text tyle={[Typography.body2]}>{I18n.t('TOTAL')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.state.montant - this.commissionsFees(this.state.montant, taux_com_client_depot, frais_min_banque_depot)}</Text>
</View>
</View>
</View>
</View>
<Dialog.Button bold={true} label={I18n.t('CANCEL_LABEL')} onPress={() => {
this.setState({
isModalConfirmVisible: false
});
}} />
<Dialog.Button bold={true} label={I18n.t('SUBMIT_LABEL')} onPress={() => {
this.setState({
isModalConfirmVisible: false,
isDataSubmit: true
});
this.props.depositAction({
numCarte: parseInt((this.state.creditCardInput.values.number).replace(/ /g, ' ')),
cvv: this.state.creditCardInput.values.cvc,
expiration_date: this.state.creditCardInput.values.expiry,
type: "credit",
montant: this.state.montant,
id_wallet: this.state.id
});
}} />
</Dialog.Container>
);
{/* <Dialog
visible={this.state.isModalConfirmVisible}
onTouchOutside={() => {
this.setState({ isModalConfirmVisible: false });
@ -215,14 +275,19 @@ class WalletDepot extends Component {
</View>
</DialogContent>
</Dialog>
)
</Dialog> */}
}
onSubmitDeposit = () => {
const { creditCardInput } = this.state;
if (this.isMontantValid().isValid && creditCardInput.valid) {
console.log("Is Montant Valid", this.isMontantValid.isValid);
console.log("creditCardInput Valid", creditCardInput.valid);
this.setState({
numCarte: parseInt((creditCardInput.values.number).replace(/ /g, ' ')),
cvv: creditCardInput.values.cvc,
@ -293,7 +358,8 @@ class WalletDepot extends Component {
render() {
const { error } = this.props;
console.log("Wallet Depot Props", this.props);
console.log("Wallet Depot State", this.state);
return (
<View style={[styles.container]}>

View File

@ -60,6 +60,7 @@ class WalletDetail extends Component {
this.heightImageBanner = Utils.scaleWithPixel(250, 1);
this.marginTopBanner = this.heightImageBanner - this.state.heightHeader - 40;
this.isHomeRootView = this.props.navigation.state.params.hasOwnProperty('agentId');
IlinkEmitter.on("langueChange", this.updateLangue.bind(this));
@ -104,7 +105,7 @@ class WalletDetail extends Component {
static navigationOptions = ({ navigation }) => {
return {
//headerTitle: this.props.navigation.state.params.wallet.network,
//title: this.isHomeRootView ? this.props.navigation.state.params.wallet.network,
headerStyle: {
backgroundColor: Color.primaryColor,
paddingTop: 10
@ -119,16 +120,18 @@ class WalletDetail extends Component {
const { result } = this.props;
if (this.props.navigation.state.params.hasOwnProperty('agentId')) {
console.log("RESULT WALLET FETCH", result);
if (result !== null) {
const wallet = Array.isArray(result) ? result[0] : result;
this.props.getWalletTransactionHistory(wallet.id);
if (typeof result.response !== 'undefined') {
const wallet = result.response[0];
//this.props.getWalletTransactionHistory(wallet.id);
this.setState({
wallet
wallet: wallet
})
}
}
}
}
shouldComponentUpdate(nextProps, nextState) {
if (this.state.triggerTransferCommission !== nextState.triggerTransferCommission) {
@ -203,10 +206,14 @@ class WalletDetail extends Component {
refresh = () => {
const { agentId, wallet } = this.props.navigation.state.params;
if (typeof agentId === "undefined")
if (typeof agentId === "undefined") {
this.props.getWalletActivated(wallet.agentId);
else
this.props.getWalletTransactionHistory(wallet.id);
}
else {
this.props.getWalletActivated(agentId);
//this.props.getWalletTransactionHistory(wallet.id);
}
}
renderTabBar = props => (
@ -425,6 +432,8 @@ class WalletDetail extends Component {
{this.renderAccountDetail(wallet)}
{!this.isHomeRootView && (
<>
<View style={[styles.checkDefault, { borderBottomColor: Color.borderColor }]}>
<Text
style={[Typography.title3, Typography.semibold]}>
@ -496,9 +505,13 @@ class WalletDetail extends Component {
</TouchableOpacity>
</View>
</View>
</>
)}
{this.renderHistoryTransaction()}
{!this.isHomeRootView && this.renderHistoryTransaction()}
</View>
</View>
</ScrollView>
@ -523,11 +536,11 @@ class WalletDetail extends Component {
style={[styles.paymentItem, { borderBottomColor: Color.borderColor }]}>
<View style={{ flexDirection: 'row', alignItems: 'center' }}>
<View style={styles.iconContent}>
<Icon name={item.type === 'credit' ? 'arrow-top-left' : 'arrow-bottom-right'}
<Icon name={item.type === 'debit' ? 'arrow-top-left' : 'arrow-bottom-right'}
color={Color.primaryColor} size={20} />
</View>
<View>
{item.type === 'credit' ? (
{item.type === 'debit' ? (
<Text style={Typography.body1}>{I18n.t('WITHDRAWAL_TRANSACTION_HISTORY_DESCRIPTION')} {item.montant}</Text>
) :
(
@ -651,9 +664,6 @@ class WalletDetail extends Component {
renderDialogTransferCommissionResponse = () => {
const { resultTransferCommission, errorTransferCommission } = this.props;
console.log("resultTransferCommission", resultTransferCommission);
console.log("errorTransferCommission", errorTransferCommission);
if (errorTransferCommission !== null) {
if (typeof errorTransferCommission.data !== 'undefined') {
Alert.alert(
@ -674,7 +684,7 @@ class WalletDetail extends Component {
if (resultTransferCommission !== null) {
if (resultTransferCommission.response !== null) {
Alert.alert(
I18n.t("SUCCESS"),
I18n.t("SUCCESS_TRANSFER_COMMISSION"),
I18n.t("COMMISSION_TRANSFER_SUCCESS"),
[
{
@ -701,7 +711,7 @@ class WalletDetail extends Component {
}
render() {
console.log("THE PROPS", this.props);
console.log("WALLET DETAILS PROPS", this.props);
const { resultTransaction, resultTransferCommission } = this.props;
const isHomeRootView = this.props.navigation.state.params.hasOwnProperty('agentId');
return (

View File

@ -14,7 +14,8 @@ import { IlinkEmitter } from "../../utils/events";
import { CreditCardInput } from "react-native-credit-card-input";
import { Typography, FontWeight } from '../../config/typography';
import depositAction from '../../webservice/DepositApi';
import Dialog, { DialogContent, DialogTitle, DialogFooter, DialogButton } from 'react-native-popup-dialog';
import Dialog from "react-native-dialog";
//import Dialog, { DialogContent, DialogTitle, DialogFooter, DialogButton } from 'react-native-popup-dialog';
let moment = require('moment-timezone');
import 'moment/locale/fr'
import 'moment/locale/es-us'
@ -145,7 +146,65 @@ class WalletRetrait extends Component {
return (
<Dialog
<Dialog.Container useNativeDriver={true} visible={this.state.isModalConfirmVisible}>
<Dialog.Title>{I18n.t('MODIFY_AMOUNT')}</Dialog.Title>
<View>
<View style={[styles.blockView, { borderBottomColor: Color.borderColor }]}>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text style={[style.body2]}>{I18n.t('AMOUNT')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.state.montant}</Text>
</View>
</View>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text tyle={[Typography.body2]}>{I18n.t('COMMISSION_FEES')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.commissionsFees(this.state.montant, taux_com_client_retrait)}</Text>
</View>
</View>
</View>
<View style={{ paddingVertical: 10 }}>
<View style={{ flexDirection: 'row', marginTop: 10 }}>
<View style={{ flex: 1 }}>
<Text tyle={[Typography.body2]}>{I18n.t('TOTAL')}</Text>
</View>
<View style={{ flex: 1, alignItems: 'flex-end' }}>
<Text style={[Typography.caption1, Color.grayColor]}>{this.state.montant - this.commissionsFees(this.state.montant, taux_com_client_retrait)}</Text>
</View>
</View>
</View>
</View>
<Dialog.Button bold={true} label={I18n.t('CANCEL_LABEL')} onPress={() => {
this.setState({
isModalConfirmVisible: false
});
}} />
<Dialog.Button bold={true} label={I18n.t('SUBMIT_LABEL')} onPress={() => {
this.setState({
isModalConfirmVisible: false,
isDataSubmit: true
});
this.props.depositAction({
numCarte: parseInt((this.state.creditCardInput.values.number).replace(/ /g, ' ')),
cvv: this.state.creditCardInput.values.cvc,
expiration_date: this.state.creditCardInput.values.expiry,
type: "debit",
montant: this.state.montant,
id_wallet: this.state.id
});
}} />
</Dialog.Container>
/* <Dialog
visible={this.state.isModalConfirmVisible}
onTouchOutside={() => {
this.setState({ isModalConfirmVisible: false });
@ -214,7 +273,7 @@ class WalletRetrait extends Component {
</View>
</DialogContent>
</Dialog>
</Dialog> */
)
}

View File

@ -49,7 +49,7 @@
"PLEASE_ENTER_THE_AMOUNT": "Please enter the amount",
"EXPIRY_CARD_ERROR": "Date incorrect",
"CARD_NUMBER_ERROR": "Card number incorrect",
"AMOUNT_LABEL": "Montant",
"AMOUNT_LABEL": "Amount",
"WITHDRAWAL": "Withdrawal",
"DEMAND_SEND": "Demand send",
"WITHDRAWAL_DESCRIPTION": "Make a withdrawal",
@ -141,7 +141,12 @@
"ERROR_LABLE": "Erreur",
"ERROR_TRANSFER_COMMISSION": "Commissions transfer error",
"ERROR_FILTER_TEXT": "Problem encountered while filtering.",
"ERROR_TREATMENT_DEMAND": "Request processing error",
"REFUSER_DEMANDE": "Reject the request",
"ACCEPTER_DEMANDE": "Accept the request",
"REFUSED": "Refuse",
"YOUR_THERE": "You are here",
"SUCCESS_TRANSFER_COMMISSION": "Transfert effectué",
"FILTER": "Filter",
"QUIT": "Quit",
"QUIT_": "Quit",
@ -166,6 +171,8 @@
"OLD_PASSWORD": "Old password",
"NEW_PASSWORD": "New password",
"CONFIRM_NEW_PASSWORD": "Confirm new password",
"MODIFY_AMOUNT": "Modify amount",
"ENTER_NEW_AMOUNT_TO_SEND": "Enter the new amount to send",
"AMOUNT": "Amount",
"STATUS": "Status",
"CANCEL": "Exit",
@ -199,7 +206,7 @@
"SUPERVISOR_NUMBER": "Number of supervisors",
"GEOLOCATED_NUMBER": "Number of points per supervisor",
"ACTIVATE_ACCOUNT": "Activate account",
"SEND": "Send!",
"SEND": "Send",
"CHANGE_INFORMATION": "Change my information",
"VALIDATE": "Validate",
"CONNECT": "Connection",

View File

@ -143,6 +143,11 @@
"ERROR_LABLE": "Erreur",
"ERROR_TRANSFER_COMMISSION": "Erreur de transfert des commissions",
"ERROR_FILTER_TEXT": "Probleme rencontré lors du filtrage.",
"ERROR_TREATMENT_DEMAND": "Erreur de traitement de la demande",
"REFUSER_DEMANDE": "Refuser la demande",
"REFUSED": "Refusé",
"ACCEPTER_DEMANDE": "Accepter la demande",
"SUCCESS_TRANSFER_COMMISSION": "Transfert de commission",
"YOUR_THERE": "Vous êtes ici",
"FILTER": "Filtrer",
"QUIT": "Quitter",
@ -168,6 +173,8 @@
"OLD_PASSWORD": "Ancien mot de passe",
"NEW_PASSWORD": "Nouveau mot de passe",
"CONFIRM_NEW_PASSWORD": "Confirmerzle nouveau mot de passe",
"MODIFY_AMOUNT": " Modifier le montant",
"ENTER_NEW_AMOUNT_TO_SEND": " Entrer le nouveau montant à envoyer",
"AMOUNT": "Montant",
"STATUS": "Statut",
"CANCEL": "Quitter",

View File

@ -0,0 +1,43 @@
import { creditCancelDemand } from "./IlinkConstants";
import { store } from "../redux/store";
import axios from "axios";
import { fetchTreatCreditCancelPending, fetchTreatCreditCancelSucsess, fetchTreatCreditCancelError, fetchTreatCreditCancelReset } from "../redux/actions/CreditCancelDemandAction";
export const treatCancelDemand = (idDemand) => {
const auth = store.getState().authKeyReducer;
const authKey = auth !== null ? `${auth.authKey.token_type} ${auth.authKey.access_token}` : '';
return dispatch => {
dispatch(fetchTreatCreditCancelPending());
axios({
url: `${creditCancelDemand}/${idDemand}`,
method: 'PUT',
headers: {
'Authorization': authKey
}
})
.then(response => {
console.log(response);
dispatch(fetchTreatCreditCancelSucsess(response));
})
.catch(error => {
console.log(error);
dispatch(fetchTreatCreditCancelError(error.message));
if (error.response)
dispatch(fetchTreatCreditCancelError(error.response));
else if (error.request)
dispatch(fetchTreatCreditCancelError(error.request))
else
dispatch(fetchTreatCreditCancelError(error.message))
});
}
}
export const creditCancelResetReducer = () => {
return dispatch => {
dispatch(fetchTreatCreditCancelReset());
}
}

View File

@ -0,0 +1,49 @@
import { creditTreatDemand } from "./IlinkConstants";
import { store } from "../redux/store";
import axios from "axios";
import { fetchTreatCreditDemandPending, fetchTreatCreditDemandSucsess, fetchTreatCreditDemandError, fetchTreatCreditDemandReset } from "../redux/actions/CreditTreatDemandActions";
export const treatCreditDemand = (idDemand, montant) => {
let dataToSend = {};
if (typeof montant !== 'undefined')
dataToSend = { "montant": montant };
const auth = store.getState().authKeyReducer;
const authKey = auth !== null ? `${auth.authKey.token_type} ${auth.authKey.access_token}` : '';
return dispatch => {
dispatch(fetchTreatCreditDemandPending());
axios({
url: `${creditTreatDemand}/${idDemand}`,
method: 'PUT',
headers: {
'Authorization': authKey
},
data: dataToSend
})
.then(response => {
console.log(response);
dispatch(fetchTreatCreditDemandSucsess(response));
})
.catch(error => {
console.log(error);
dispatch(fetchTreatCreditDemandError(error.message));
if (error.response)
dispatch(fetchTreatCreditDemandError(error.response));
else if (error.request)
dispatch(fetchTreatCreditDemandError(error.request))
else
dispatch(fetchTreatCreditDemandError(error.message))
});
}
}
export const creditDemandResetReducer = () => {
return dispatch => {
dispatch(fetchTreatCreditDemandReset());
}
}

View File

@ -32,7 +32,9 @@ export const loadDemandeCredit= async ()=>{
}
export const loadMyDemandeCredit = async () => {
const user = await readUser();
const data={"tag":"credit_demands_of_agent",id:user.agentId
console.log("USER ID", user.agentId);
const data = {
"tag": "credit_demands_of_agent", id: user.agentId
, "lang": I18n.currentLocale(),
test: isDebugMode
@ -57,7 +59,8 @@ export const loadMyDemandeCredit= async ()=>{
}
export const updateCreditDemand = (phone, id) => {
const data={"tag":"update_ask_credit","phone":phone,"id":id,
const data = {
"tag": "update_ask_credit", "phone": phone, "id": id,
"lang": I18n.currentLocale(),
test: isDebugMode
}
@ -115,11 +118,13 @@ export const sendDemande= async (credit)=>{
return -1;
}
export const sendDemandeSpecificque = async (credit, phone, code_membre) => {
let data={"tag":"ask_credit",
let data = {
"tag": "ask_credit",
"phone": phone,
test: isDebugMode,
code: code_membre,
"montant":credit,"lang":I18n.currentLocale()};
"montant": credit, "lang": I18n.currentLocale()
};
let response = await fetch(demandeActionUrl, {
method: 'POST',

View File

@ -19,6 +19,8 @@ export const locationActionUrl = baseUrl + '/interacted/LocationAction.php';
export const demandeActionUrl = baseUrl + '/interacted/DemandeAction.php';
export const configActionUrl = baseUrl + '/interacted/ConfigAction.php';
export const walletActionUrl = testBaseUrl + '/walletService/wallets';
export const creditTreatDemand = testBaseUrl + '/walletService/credits/treatDemand';
export const creditCancelDemand = testBaseUrl + '/walletService/credits/cancelDemand';
export const transactionUrl = testBaseUrl + '/walletService/transactions';
export const transferCommission = testBaseUrl + '/walletService/virement';
export const authKeyUrl = testBaseUrl + '/oauth/token';

View File

@ -6326,7 +6326,7 @@ react-native-action-button@^2.8.5:
dependencies:
prop-types "^15.5.10"
react-native-animatable@^1.3.2:
react-native-animatable@^1.2.4, react-native-animatable@^1.3.2:
version "1.3.3"
resolved "https://registry.yarnpkg.com/react-native-animatable/-/react-native-animatable-1.3.3.tgz#a13a4af8258e3bb14d0a9d839917e9bb9274ec8a"
integrity sha512-2ckIxZQAsvWn25Ho+DK3d1mXIgj7tITkrS4pYDvx96WyOttSvzzFeQnM2od0+FUMzILbdHDsDEqZvnz1DYNQ1w==
@ -6410,6 +6410,14 @@ react-native-device-info@^2.1.1:
resolved "https://registry.yarnpkg.com/react-native-device-info/-/react-native-device-info-2.3.2.tgz#db2b8f135aaf2515583e367ab791dcc7d2f0d14c"
integrity sha512-ccpPuUbwhw5uYdVwN1UJp6ykMZz6U/u82HNM3oJ7O6MP8RIMlMDkHbqR4O0sDtUSuRMGiqqRzFtmOLFYeQ0ODw==
react-native-dialog@^5.6.0:
version "5.6.0"
resolved "https://registry.yarnpkg.com/react-native-dialog/-/react-native-dialog-5.6.0.tgz#8c36a1e9f397eba0cea88821ebcf92f029236a1a"
integrity sha512-pUTxHJHzErMY+JaDRSMKiCbJTEdy2Ik4hcNOwasOlxpj6S6tT5SonLsrLPGBCO0XpTOySE0qVzuikmKgUDZfig==
dependencies:
prop-types "^15.7.2"
react-native-modal "^9.0.0"
react-native-elements@^1.1.0:
version "1.2.7"
resolved "https://registry.yarnpkg.com/react-native-elements/-/react-native-elements-1.2.7.tgz#1eca2db715c41722aeb67aea62bd2a4621adb134"
@ -6564,6 +6572,14 @@ react-native-material-textfield@^0.12.0:
dependencies:
prop-types "^15.5.9"
react-native-modal@^9.0.0:
version "9.0.0"
resolved "https://registry.yarnpkg.com/react-native-modal/-/react-native-modal-9.0.0.tgz#0bfd0770361a2e5c6e0072bfdb0f1277f9662dba"
integrity sha512-j4xeIK9noHU/ksp2Ndc8NI1qJvjApToqGvqLEu2wtYeaISanbhtd0S3V4hZkSlCa3DZtegl6aaMZBLeH1q6xfA==
dependencies:
prop-types "^15.6.2"
react-native-animatable "^1.2.4"
react-native-paper@^2.16.0:
version "2.16.0"
resolved "https://registry.yarnpkg.com/react-native-paper/-/react-native-paper-2.16.0.tgz#5a9edd5615bb010ec0d29cbfd5524c2944b2505d"
@ -6631,6 +6647,21 @@ react-native-root-siblings@^3.2.1:
prop-types "^15.6.2"
static-container "^1.0.0"
react-native-root-siblings@^4.0.0:
version "4.0.6"
resolved "https://registry.yarnpkg.com/react-native-root-siblings/-/react-native-root-siblings-4.0.6.tgz#6dd7eedb725faacd7ba19c159dd279cf2e6d8476"
integrity sha512-u/MaJLdD3bnshDFg8HWB0Xys1xlkQy6++3QthQlYw4kOFElobb6V1IIn5r46JvBTr9cf6dXsrFC4zPVXuwW1ww==
dependencies:
static-container "^1.5.1"
react-native-root-toast@^3.2.1:
version "3.2.1"
resolved "https://registry.yarnpkg.com/react-native-root-toast/-/react-native-root-toast-3.2.1.tgz#f456d029f5c5b76e4b686334f25371465478a3be"
integrity sha512-BNf6LKMqcIAonKgqCGQWk+1lduFqSjPYbEF0FygMZbXhODRTvrGUAvAgV6kfamVPOkKHUkPU7dnnvmgEQ8ZDzQ==
dependencies:
prop-types "^15.5.10"
react-native-root-siblings "^4.0.0"
react-native-safe-area-view@^0.12.0:
version "0.12.0"
resolved "https://registry.yarnpkg.com/react-native-safe-area-view/-/react-native-safe-area-view-0.12.0.tgz#5c312f087300ecf82e8541c3eac25d560e147f22"
@ -7629,7 +7660,7 @@ stacktrace-parser@^0.1.3:
dependencies:
type-fest "^0.7.1"
static-container@^1.0.0:
static-container@^1.0.0, static-container@^1.5.1:
version "1.5.1"
resolved "https://registry.yarnpkg.com/static-container/-/static-container-1.5.1.tgz#9d7a94e04dea864539a7b6a1304843ada740dc19"
integrity sha512-OFChfLKIvSzaMA3otS5CEabJTIzHFPhMxogIT+io4F207PXTvS6woFyjXIyXyqMIYAhryePGeFZYC6uLcG1lpA==