React Native 네트워크 5

윤수환·2025년 3월 20일

React Native

목록 보기
26/26

변경점
API.tsx

import axios from 'axios'

const instance = axios.create ({
    baseURL: 'http://192.168.0.4:3000',
    timeout: 10000
})

export default {
    test() {
        return instance.get('/taxi/test')
    },
    login(id:string, pw:string) {
        return instance.post('./taxi/login', {userId: id, userPw: pw})
    },
    register(id:string, pw:string) {
        return instance.post('/taxi/register', {userId: id, userPw: pw})
    },
    list(id:string) {
        return instance.post('/taxi/list', {userId: id})
    },
    call(id: string, startLat: string, startLng: string, startAddr: string,
        endLat: string, endLng: string, endAddr: string) {
        return instance.post('/taxi/call', {userId: id,
            startLat: startLat, startLng: startLng, startAddr: startAddr,
            endLat: endLat, endLng: endLng, endAddr: endAddr})
    },
    geoCoding(coords:any, key:string) {
        let url = 'https://maps.googleeapis.com/maps/api/geocode/json'
        let lat = coords.latitude
        let lng = coords.longitude

        return axios.get(`${url}?latlng=${lat}, ${lng}&key=${key}&language=ko`)
    }
}

Main_Map.tsx

import { JSX } from "react";
import { SafeAreaView, StyleSheet, Text, View, Modal, TouchableOpacity, Alert } from "react-native";
import Icon from 'react-native-vector-icons/FontAwesome';
import { widthPercentageToDP as wp, heightPercentageToDP as hp } from "react-native-responsive-screen";
import { useState, useRef } from 'react';
import MapView, {PROVIDER_GOOGLE, Marker, Polyline} from "react-native-maps";
import { GooglePlacesAutocomplete } from "react-native-google-places-autocomplete";
import api from './API';
import Geolocation from "@react-native-community/geolocation";
import AsyncStorage from "@react-native-async-storage/async-storage";
import { StackNavigationProp } from "@react-navigation/stack";
import { useNavigation, ParamListBase } from '@react-navigation/native'

function Main_Map() : JSX.Element {
    console.log("-- Main_Map()")

    const navigation = useNavigation<StackNavigationProp<ParamListBase>>()

    const callTaxi = async() => {
        let userId = await AsyncStorage.getItem('userId') || ""
        let startAddr = autocomplete1.current.getAddressText()
        let endAddr = autocomplete2.current.getAddressText()

        let startLat = `${marker1.latitude}`
        let startLng = `${marker1.longitude}`
        let endLat = `${marker2.latitude}`
        let endLng = `${marker2.longitude}`

        if(!(startAddr && endAddr)) {
            Alert.alert("알림", "출발지/도착지가 모두 입력되어야 합니다." ,[
                {text: '확인', style: 'cancel'}
            ])
            return
        }

        api.call(userId, startLat, startLng, startAddr, endLat, endLng, endAddr)
        .then(response => {
            let {code, message} = response.data[0]
            let title = "알림"
            if (code==0) {
                navigation.navigate("Main_List")
            }
            else {
                title = "오류"
            }

            Alert.alert(title, message, [
                {text: '확인', style: 'cancel'}
            ])
        })
        .catch(err => {
            console.log(JSON.stringify(err))
        })
    }

    const [loading, setLoading] = useState(false)
    const [selectedLatLng, setSelectedLatLng] = useState({
        latitude:0, longitude:0
    })
    const [selectedAddress, setSelectedLatAddress] = useState('')

    const mapRef : any = useRef(null)

    const [initalRegion, setInitalRegion] = useState({
        latitude: 37.5666612,
        longitude: 126.9783785,
        latitudeDelta: 0.0922,
        longitudeDelta: 0.0421
    })

    const [showBtn, setShowBtn] = useState(false)

    const handleLongPress = async(event:any) => {
        const { coordinate } = event.nativeEvent

        setSelectedLatLng(coordinate)

        setLoading(true)
        api.geoCoding(coordinate, query.key)
        .then(response => {
            setSelectedLatAddress(response.data.results[0].formatted_address)
            setShowBtn(true)
            setLoading(false)
        })
        .catch(err => {
            console.log(JSON.stringify(err))
            setLoading(false)
        })
    }

    const autocomplete1 : any = useRef(null)
    const autocomplete2 : any = useRef(null)


    const handleAddMarker = (title:string) => {
        if (selectedAddress) {
            if (title=="출발지") {
                setMarker1(selectedLatLng)
                if (autocomplete1.current) {
                    autocomplete1.current.setAddressText(selectedAddress)
                }
            }
        }
        else {
            setMarker2(selectedLatLng)
            if (autocomplete2.current) {
                autocomplete2.current.setAddressText(selectedAddress)
            }
        }
        setShowBtn(false)
    }

    let query = {
        key: "AIzaSyCxAEv4QYaJJxSTf46MC5BujoJcsavmjJw",
        language: "ko",
        components: "country:kr"
    }

    const [marker1, setMarker1] = useState({latitude:0, longitude:0})
    const [marker2, setMarker2] = useState({latitude:0, longitude:0})

    const onSelectAddr = (data:any, details:any, type:string) => {
        if (details) {
            let lat = details.geometry.location.lat
            let lng = details.geometry.location.lng

            if(type=="start") {
                setMarker1({latitude:lat, longitude:lng})
                if (marker2.longitude==0) {
                    setInitalRegion({
                        latitude:lat, longitude:lng,
                        latitudeDelta: 0.0073, longitudeDelta: 0.0064
                    })
                }
            }
            else {
                setMarker2({latitude:lat, longitude:lng})
                if (marker1.longitude==0) {
                    setInitalRegion({
                        latitude:lat, longitude:lng,
                        latitudeDelta: 0.0073, longitudeDelta: 0.0064
                    })
                }
            }
        }
    }

    if (marker1.latitude!=0 && marker2.latitude!=0) {
        if (mapRef.current) {
            mapRef.current.fitToCoordinates([marker1, marker2], {
                edgePadding: {top: 120, right: 50, bottom: 50, left: 50},
                animated:true
            })
        }
    }

    const setMyLocation = () => {
        setLoading(true)

        Geolocation.getCurrentPosition((position) => {
            const {latitude, longitude} = position.coords

            let coords = {latitude, longitude}
            setMarker1(coords)
            setInitalRegion({latitude:0, longitude:0, latitudeDelta:0, longitudeDelta: 0})
            setInitalRegion({latitude:latitude, longitude:longitude,
                latitudeDelta:0.0073, longitudeDelta:0.0064
            })

            api.geoCoding(coords, query.key)
            .then(response => {
                let addr = response.data.results[0].formatted_address
                autocomplete1.current.setAddressText(addr)
                setLoading(false)
            })
            .catch(err => {
                console.log(JSON.stringify(err))
                setLoading(false)
            })
        },
        (error) => {
            setLoading(false)
            console.log("Geolocation 오류 / error = " + JSON.stringify(error))
        },
        {
            enableHighAccuracy:false,
            timeout: 10000,
            maximumAge: 1000
        }
    )
    }

    return (
        <SafeAreaView style={styles.container}>
            <MapView style={styles.container} provider={PROVIDER_GOOGLE}
            region={initalRegion} ref={mapRef}
            onLongPress={handleLongPress}
            onPress={() => {setShowBtn(false)}}
            >
                <Marker coordinate={marker1} title="출발 위치"/>
                <Marker coordinate={marker2} title="도착 위치" pinColor="blue"/>
                {marker1.latitude !=0 && marker2.latitude !=0 && (
                    <Polyline
                    coordinates={[marker1, marker2]}
                    strokeColor="blue"
                    strokeWidth={3}/>
                )}
            </MapView>

            <View style={{position:'absolute', width:'100%', height:'100%', padding:10}}>
                <View style={{position:'absolute', padding:wp(2)}}>
                    <View style={{width:wp(75)}}>
                        <GooglePlacesAutocomplete
                            ref={autocomplete1}
                            onPress={(data, details) => onSelectAddr(data, details, 'start')}
                            minLength={2}
                            placeholder="출발지 검색"
                            query={query}
                            keyboardShouldPersistTaps={"handled"}
                            fetchDetails={true}
                            enablePoweredByContainer={false}
                            onFail={(error) => console.log(error)}
                            onNotFound={() => console.log("no results")}
                            styles={autocompleteStyles}
                            />
                    </View>
                    <View style={{width:wp(75)}}>
                        <GooglePlacesAutocomplete
                            ref={autocomplete2}
                            onPress={(data, details) => onSelectAddr(data, details, 'end')}
                            minLength={2}
                            placeholder="도착지 검색"
                            query={query}
                            keyboardShouldPersistTaps={"handled"}
                            fetchDetails={true}
                            enablePoweredByContainer={false}
                            onFail={(error) => console.log(error)}
                            onNotFound={() => console.log("no results")}
                            styles={autocompleteStyles}
                            />
                    </View>
                </View>
                <TouchableOpacity 
                style={[styles.button,
                    {position:'absolute', width: wp(18), top:wp(2), right:wp(2), height: 90, justifyContent:'center'}]}
                    onPress={callTaxi}
                    >
                    <Text style={styles.buttonText}>호출</Text>
                </TouchableOpacity>
            </View>
            {/* 내 위치 */}
            <TouchableOpacity style={[{position:'absolute', bottom:20, right:20}]}
            onPress={setMyLocation}
            >
                <Icon name="crosshairs" size={40} color={'#3498db'}/>
            </TouchableOpacity>

            <View style={{position:'absolute', top: hp(50)-45, left: wp(50)-75, height:90, width:150}}>
                <TouchableOpacity style={[styles.button, {flex:1, marginVertical:1}]}
                onPress={()=>handleAddMarker('출발지')}
                >
                    <Text style={styles.buttonText}>출발지로 등록</Text>
                </TouchableOpacity>
                <TouchableOpacity style={[styles.button, {flex:1}]}
                onPress={()=>handleAddMarker('출발지')}
                >
                    <Text style={styles.buttonText}>도착지로 등록</Text>
                </TouchableOpacity>
            </View>
            
            <Modal transparent={true} visible={loading}>
                <View style={{flex:1, justifyContent:'center', alignItems:'center'}}>
                    <Icon name="spinner" size={50} color="blue"/>
                    <Text style={{backgroundColor:'white', color:'black', height:20}}>Loading...</Text>
                </View>
            </Modal>

        </SafeAreaView>
    )
}

const autocompleteStyles = StyleSheet.create ({
    textInputContainer: {
        width: '100%',
        backgroundColor:'#e9e9e9',
        borderRadius: 8,
        height: 40
    },
    textInput: {
        height: 40,
        color: '#5d5d5d',
        fontSize: 16
    },
    predefindPlacesDescription: {
        color: '#1faadb',
        zIndex: 1
    }
})

const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        width: '100%'
    },
    button: {
        backgroundColor: '#3498db',
        paddingVertical: 10,
        paddingHorizontal: 20,
        borderRadius: 5
    },
    buttonDisable: {
        backgroundColor: 'gray',
        paddingVertical: 10,
        paddingHorizontal: 20,
        borderRadius: 5
    },
    buttonText: {
        color: 'white',
        fontSize: 16,
        textAlign: 'center'
    },
    input: {
        height: 40,
        borderWidth: 2,
        borderColor: 'gray',
        marginVertical: 1,
        padding: 10
    }
})

export default Main_Map

Main_List.tsx

import React from 'react';
import { JSX } from "react";
import { SafeAreaView, StyleSheet, Text, View, FlatList, RefreshControl, Modal, Alert } from "react-native";
import { widthPercentageToDP as wp, heightPercentageToDP as hp } from "react-native-responsive-screen";
import { useState } from 'react';
import { useFocusEffect } from "@react-navigation/native";
import Icon from 'react-native-vector-icons/FontAwesome';
import AsyncStorage from '@react-native-async-storage/async-storage';
import api from './API';

function Main_List() : JSX.Element {
    console.log("-- Main_List()")

    const [callList, setCallList] = useState([])
    const [loading, setLoading] = useState(false)

    useFocusEffect(React.useCallback(() => {
        requestCallList()
    },[]))

    const requestCallList = async() => {
        setLoading(true)
        let userId = await AsyncStorage.getItem('userId') || ""
        api.list(userId)
        .then(response => {
            let {code, message, data} = response.data[0]
            if(code == 0) {
                setCallList(data)
            }
            else {
                Alert.alert("오류", message, [{
                    text: "확인",
                    onPress: () => console.log('cancel pressed'),
                    style: 'cancel'
                }])
            }
            setLoading(false)
        })
        .catch(err => {
            console.log(JSON.stringify(err))
            setLoading(false)
        })

    }

    const Header = () => {
        <View style={styles.header}>
            <Text style={[styles.headerText, {width:wp(80)}]}>출발지 / 도착지</Text>
            <Text style={[styles.headerText, {width:wp(20)}]}>상태</Text>
        </View>
    }

    const ListItem = (row:any) => {
        console.log("row = " + JSON.stringify(row))
        return (
            <View style={{flexDirection:'row', marginBottom:5, width:wp(100)}}>
                <View style={{width:wp(80)}}>
                    <Text style={styles.textForm}>{row.item.start_addr}</Text>
                    <Text style={[styles.textForm, {borderTopWidth:0}]}>{row.item.end_addr}</Text>
                    <Text style={styles.textForm}>{row.item.formatted_time}</Text>
                </View>
                <View style={{width:wp(20), alignItems:'center', justifyContent:'center'}}>
                    <Text>{row.item.call_state}</Text>
                </View>
            </View>
        )
    }


    return (
        <SafeAreaView style={styles.container}>
            <FlatList style={{flex:1}}
            data={callList}
            ListHeaderComponent={Header}
            renderItem={ListItem}
            keyExtractor={(item:any) => item.id}
            refreshControl={
                <RefreshControl refreshing={loading} onRefresh={requestCallList}/>
            }
            />
            <Modal transparent={true} visible={loading}>
                <View style={{flex:1, justifyContent:'center', alignItems:'center'}}>
                    <Icon name='spinner' size={50} color={'#3498db'}/>
                    <Text style={{color:'black'}}>Loading...</Text>
                </View>
            </Modal>
        </SafeAreaView>
    )
}

const styles = StyleSheet.create({
    container: {
        flex: 1,
        justifyContent: 'center',
        alignItems: 'center',
        width: '100%',
        backgroundColor: 'white'
    },
    header: {
        flexDirection: 'row',
        height: 50,
        marginBottom: 5,
        backgroundColor: '#3498db',
        color: 'white',
        alignItems: 'center'
    },
    headerText: {
        fontSize: 18,
        textAlign: 'center',
        color: 'white'
    },
    textForm: {
        flex: 1,
        borderWidth: 1,
        borderColor: 'white',
        height:hp(5),
        paddingLeft: 10,
        paddingRight: 10
    }
})

export default Main_List

패키지
npm install @react-native-community/geolocation

index.js

var express = require('express');
var router = express.Router();

const db = require('../database/db_connect')
const { use } = require('.');
const admin = require('firebase-admin');
const { response } = require('../app');

/* GET home page. */
router.get('/', function(req, res, next) {
  res.render('index', { title: 'Express' });
});

const updateFcm = (fcmToken, table, idColName, id) => {
  const queryStr = `UPDATE ${table} SET fcm_token="${fcmToken}" WHERE ${idColName}="${id}"`
  console.log(queryStr, function(err, rows, fields) {
    if(err) {
      console.log('updateFcm / err : ' + JSON.stringify(err))
    }
  })
}

const sendPushToAlldriver = () => {
  let queryStr = `SELECT fcm_token from tb_driver`

  console.log(">> queryStr = " + queryStr)

  db.query(queryStr, function(err, rows, fields) {
    if(!err) {
      for (row of rows) {
        console.log("allDriver - fcm_token = " + row.fcm_token)
        if(row.fcm_token) {
          sendFcm(row.fcm_token,"배차 요청이 있습니다.")
        }
      }
    }
  })
}

const sendPushToUser = (userId) => {
  let queryStr = `SELECT fcm_token FROM tb_user WHERE user_id="${userId}"`
  console.log(">> push user - queryStr = " + queryStr)

  db.query(queryStr, function(err, rows, fields) {
    if(!err) {
      console.log(">> push user - rows = " + JSON.stringify(rows))
      if(Object.keys(rows).length>0 && rows[0].fcm_token) {
        sendFcm(rows[0].fcm_token, "배차가 완료되었습니다.")
      }
      else {
        console.log("Push 전송 실패")
      }
    }
    else {
      console.log(">> push user - err : " + err)
    }
  })
}

router.get('/taxi/test', function (req, res, next) {
  
  db.query('select * from tb_user', (err, rows, fields) => {
    if (!err) {
      console.log("test / rows =" + JSON.stringify(rows))
      res.json([{code:0, data:rows}])
    }
    else {
      console.log("test / err: " + err)
      res.json([{code:1, data:err}])
    }
  })
})

router.post('/taxi/login', function (req, res, next) {
  console.log("login / req.body " + JSON.stringify(req.body))

  let userId = req.body.userId
  let userPw = req.body.userPw
  let fcmToken = req.body.fcmToken || ""

  let queryStr = `SELECT * FROM tb_user WHERE user_id="${userId}" AND user_pw="${userPw}"`
  console.log("login / queryStr = " + queryStr)
  db.query(queryStr, (err, rows, fields) => {
    if (!err) {
      console.log("login / rows = " + JSON.stringify(rows))
      let len = Object.keys(rows).length
      console.log("login / len = " + len)
      let code = len==0 ? 1 : 0
      let message = len == 0 ? "아이디 또는 비밀번호가 잘못 입력되었습니다" : "로그인 성공"

      if(code==0) {
        updateFcm(fcmToken, 'tb_user', 'user_id', userId)
      }

      res.json([{code: code}, {message: message}])
    }
    else {
      console.log("login / err : " + err)
      res.json([{code: 1, message: err}])
    }
  })
})

router.post('/taxi/register', function (req,res) {
  console.log("register / req.body " + JSON.stringify(req.body))

  let userId = req.body.userId
  let userPw = req.body.userPw
  let fcmToken = req.body.fcmToken || ""

  console.log("register / userId = " + userId + ", userPw = " + userPw)
  if (!(userId && userPw)) {
    res.json([{code: 1, message: "아이디 또는 비밀번호가 없습니다."}])
    return
  }

  let queryStr = `insert into tb_user values ("${userId}", "${userPw}", "${fcmToken}")`
  console.log("register / queryStr = " + queryStr)
  db.query(queryStr, function(err,rows,fields) {
    if (!err) {
      console.log("register / rows = " + JSON.stringify(rows))
      res.json([{code: 0, message: "회원가입이 완료되었습니다."}])
    }
    else {
      console.log("register / err: " + JSON.stringify(err))
      if (err.code=="ER_DUP_ENTRY") {
        res.json([{code: 2, message: "이미 등록된 아이디입니다."}])
      }
      else {
        res.json([{code: 3, message: "알 수 없는 오류.", data: err}])
      }
    }
  })
})

router.post('/taxi/list', function (req, res) {
  console.log('list / req.body ' + JSON.stringify(req.body))
  let userId = req.body.userId
  console.log('list / userId = ' + userId)

  let queryStr = `SELECT * FROM tb_call WHERE user_id="${userId}" ORDER BY id DESC`
  console.log("list / queryStr = " + queryStr)
  db.query(queryStr, function(err, rows, fields) {
    if (!err) {
      console.log("list / rows = " + JSON.stringify(rows))
      let code = 0
      rows = rows.map(row => {
        const requestTime = new Date(row.request_time)
        const today = new Date()
        const isToday = requestTime.toDateString() === today.toDateString();

        const formattedDate = requestTime.toISOString().split('T')[0] // YYYY-MM-DD
        const formattedTime = requestTime.toTimeString().split(' ')[0].slice(0,5) //HH:mm

        row.formatted_time = isToday ? formattedTime : formattedDate;
      })
      res.json([{code: code, message: "택시 호출 목록 호출 성공", data : rows}])
    }
    else {
      console.log('err : ' + err)
      res.json([{code: 1, message: "알 수 없는 오류", data: err}])
    }
  })
})

router.post('/taxi/call', function(req, res) {
  console.log("taxi/call / req.body " + JSON.stringify(req.body))

  let userId = req.body.userId
  let startAddr = req.body.startAddr
  let startLat = req.body.startLat
  let startLng = req.body.startLng
  let endAddr = req.body.endAddr
  let endLat = req.body.endLat
  let endLng = req.body.endLng

  if (!(userId && startAddr && startLat && startLng && endAddr && endLat && endLng)) {
    //하나라도 빠지면
    res.json([{code: 1, message: "출발지 또는 도착지 정보가 없습니다."}])
    return
  }
  
  let queryStr = `INSERT INTO tb_call VALUES(NULL, "${userId}",
  "${startLat}", "${startLng}", "${startAddr}",
  "${endLat}", "${endLng}", "${endAddr}", "REQ", "", CURRENT_TIMESTAMP)`

  console.log("call / queryStr = " + queryStr)

  db.query(queryStr, function(err, rows, fields) {
    if (!err) {
      console.log("call / rows = " + JSON.stringify(rows))
      sendPushToAlldriver()
      res.json([{code: 0, message: "택시 호출이 완료되었습니다."}])
    }
    else {
      console.log("call / err : " + JSON.stringify(err))
      res.json([{code: 2, message: "택시 호출이 실패했습니다.", data: err}])
    }
  })
})

router.post('/driver/register', function(req, res) {
  console.log('driver-register / req.body ' + JSON.stringify(req.body))

  let userId = req.body.userId
  let userPw = req.body.userPw
  let fcmToken = req.body.fcmToken || ""
  
  console.log('driver-register / userId = ' + userId + ',userPw' + userPw)

  if (!(userId && userPw)) {
    res.json([{code: 1, message: "아이디 또는 비밀번호가 없습니다."}])
    return
  }

  let queryStr = `INSERT INTO tb_driver VALUES("${userId}", "${userPw}", "${fcmToken}")`
  console.log("driver-register / queryStr = " + queryStr)

  db.query(queryStr, function(err, rows, fields) {
    if (!err) {
      console.log("driver-register / rows = " + JSON.stringify(rows))
      res.json([{code: 0, message: "회원가입이 완료되었습니다."}])
    }
    else {
      console.log('driver-register / err : ' + JSON.stringify(err))
      if (err.code == "ER_DUP_ENTRY") {
        res.json([{code: 2, message: "이미 등록된 아이디입니다."}])
      }
      else {
        res.json([{code: 3, message: "알 수 없는 오류", data: err}])
      }
    }
  })
})

router.post('/driver/login', function(req, res) {
  console.log("driver-login / req.body" + JSON.stringify(req.body))

  let userId = req.body.userId
  let userPw = req.body.userPw
  let fcmToken = req.body.fcmToken || ""

  let queryStr = `SELECT * FROM tb_driver WHERE driver_id="${userId}" AND driver_pw="${userPw}"`
  console.log("driveer-login / queryStr " + queryStr)
  db.query(queryStr, (err, rows, fields) => {
    if (!err) {
      console.log("driver-login / rows = " + JSON.stringify(rows))
      let len = Object.keys(rows).length
      console.log("driver-login / len = " + len)
      let code = len == 0 ? 1 : 0
      let message = len == 0 ? "아이디 또는 비밀번호가 잘못 입력되었습니다." : "로그인 성공"

      if(code==0) {
        updateFcm(fcmToken, 'tb_driver', 'driver_id', userId)
      }

      res.json([{code: code, message: message}])
    }
    else {
      console.log("driver-login / err : " + err)
      res.json([{code: 1, message: err}])
    }
  })
})

router.post('/driver/list', function(req, res) {
  console.log("driver-list / req.body " + JSON.stringify(req.body))

  let userId = req.body.userId

  console.log("driver-list / userId = " + userId)

  let queryStr = `SELECT * FROM tb_call WHERE driver_id="${userId}"
    OR call_state="REQ" ORDER BY id DESC`

  console.log("driver-list / queryStr = " + queryStr)
  db.query(queryStr, function(err, rows, fields) {
    if (!err) {
      console.log("driver-list / rows = " + JSON.stringify(rows))
      let code = 0
      res.json([{code: code, message: "택시 호출 목록 호출 성공", data: rows}])
    }
    else {
      console.log("driver-list / err " + err)
      res.json([{code: 1, message: "알 수 없는 오류", data: err}])
    }
  })
})

router.post('/driver/accept', function(req, res) {
  console.log("driver-accept / req.body " + JSON.stringify(req.body))

  let callId = req.body.callId
  let driverId = req.body.driverId
  let userId = req.body.userId

  console.log("driver-accept / callId = " + callId + ",driverId = " + driverId)

  if(!(callId && driverId)) {
    res.json([{code: 1, message: "callId 또는 driverId가 없습니다."}])
    return
  }

  let queryStr = `UPDATE tb_call set driver_id="${driverId}", call_state="RES" WHERE id=${callId}`
  console.log("driver-accept / queryStr = " + queryStr)
  db.query(queryStr, function(err, rows, fields) {
    if(!err) {
      console.log("driver-accept / rows = " + JSON.stringify(rows))
      if(rows.affectedRows > 0) {
        sendPushToUser(userId)
        res.json([{code: 0, message: "배차가 완료되었습니다"}])
      }
      else {
        res.json([{code: 2, message: "이미 완료되었거나 존재하지 않는 콜입니다."}])
      }
    }
    else {
      console.log("driver-accept / err : " + JSON.stringify(err))
      res.json([{code: 3, message: "알 수 없는 오류", data: err}])
    }
  })

})

router.post('/push/test', function(req, res) {
  console.log("push-test / req.body " + JSON.stringify(req.body))

  let fcmToken = req.body.fcmToken
  let message = req.body.message
  
  sendFcm(fcmToken, message)

  res.json([{code: 0, message: "Push test"}])
})


const sendFcm = (fcmToken, msg) => {
  const message = {notification: {title: '알림', body: msg}, token: fcmToken}

  admin.messaging().send(message)
  .then((response) => {
    console.log("-- push 성공")
  })
  .catch((error) => {
    console.log("-- push error / " + JSON.stringify(error))
  })
}


module.exports = router;

0개의 댓글