hejianhao
2026-03-21 39a782e38707dbcd4b064ff68a8b551938fe987e
fix: 修复订单状态映射与同步逻辑,优化费用明细展示

- 提取订单状态映射函数至公共方法,消除重复逻辑
- 增加订单状态同步时的版本控制,防止状态回退
- 修复城市信息匹配函数中的代码块嵌套错误
- 在费用明细页面添加行程距离和时长的格式化显示
- 在订单详情页面添加调试日志便于问题排查
5个文件已修改
130 ■■■■■ 已修改文件
src/pages/robotaxi/home/index.tsx 32 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/robotaxi/pages/begin-route/index.tsx 17 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/robotaxi/pages/expense-description/index.tsx 42 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/robotaxi/pages/order/detail/index.tsx 1 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/utils/Robotaxi-public-method.ts 38 ●●●●● 补丁 | 查看 | 原始文档 | blame | 历史
src/pages/robotaxi/home/index.tsx
@@ -22,7 +22,8 @@
  fetchMapData,
  getCityLocation,
  getCityInfoWithId,
  getLocationByIP
  getLocationByIP,
  mapOrderStatusToTripStatus
} from '../../../utils/Robotaxi-public-method';
import { jumpTo } from '../../../utils/jump';
import { _ROBOTAXI_WS_HOST, CDN } from '../../../constants/api';
@@ -125,19 +126,6 @@
    8: '行程已结束,请尽快支付'
  }
  const mapActiveStatusToTripStatus = (status: number) => {
    if (status === 0) return 1;
    if (status === 1) return 3;
    if (status === 3 || status === 2) return 4;
    if (status === 4) return 5;
    if (status === 5) return 6;
    if (status === 6) return 6;
    if (status === 7) return 7;
    if (status === 8) return 8;
    if (status === 9) return 9;
    if (status === 10) return 9;
    return 0;
  };
  // 监听页面显示
  useDidShow(() => {
    getServicePhone().then((res) => {
@@ -186,8 +174,8 @@
            return
          }
          setOrderData(res || {});
          setTripStatus(mapActiveStatusToTripStatus(res.status || 0));
          Taro.setStorageSync('tripStatus', mapActiveStatusToTripStatus(res.status || 0));
          setTripStatus(mapOrderStatusToTripStatus(res.status || 0));
          Taro.setStorageSync('tripStatus', mapOrderStatusToTripStatus(res.status || 0));
          Taro.setStorageSync('orderId', res.id || '');
          if (!Taro.getStorageSync('startSite')) {
            Taro.setStorageSync('startSite', {
@@ -327,7 +315,7 @@
        getLocationInfo(shouldUpdateCenter);
        // 如果没有缓存上车点,且有定位权限,调用 toOrigin 回到用户当前位置
        if (!hasStartSite && auth === true) {
           toOrigin();
          toOrigin();
        }
      }
    });
@@ -536,15 +524,15 @@
            const { newMarkers, sites } = await updateMapData(res.latitude, res.longitude, cityInfo.code);
            const nearestCandidates = sites.length > 0 ? sites : newMarkers;
            const { targetMarker, minDistance } = findNearestMarker(res.latitude, res.longitude, nearestCandidates);
            // 获取吸附距离(如果本地 state 还没加载完,给个默认值 1000)
            const currentAdsorptionDistance = adsorptionDistance || 1000;
            if (minDistance < currentAdsorptionDistance && targetMarker) {
              setIsAdsorbed(true);
              setCurrentSite(targetMarker);
              setShowToolTip(true);
              // 自动将地图视角移动到吸附站点
              if (updateCenter) {
                const mapCtx = Taro.createMapContext('map');
@@ -565,7 +553,7 @@
        if (addressData) {
          const address = addressData.name || addressData.desc;
          setCurrentAddress(address);
          // 如果没有被吸附(isAdsorbed为false),才使用地址名称作为当前站点的显示名称
          setCurrentSite(prevSite => {
            // 如果之前没有站点数据或者只有基础的经纬度/名字(非正式站点)
@@ -578,7 +566,7 @@
            }
            return prevSite;
          });
          // 仅在没有吸附到站点时才将状态置为未吸附
          // 如果前面已经因为距离近而 return 了,这里就不会执行到
          setIsAdsorbed(false);
src/robotaxi/pages/begin-route/index.tsx
@@ -32,7 +32,8 @@
  convertAdcodeToCityCode,
  getCityInfoWithId,
  getDistance,
  shouldUpdateRoute
  shouldUpdateRoute,
  mapOrderStatusToTripStatus
} from '../../../utils/Robotaxi-public-method';
import {
  saveOrder,
@@ -429,6 +430,7 @@
    return 0;
  };
  // 更新地图视口内边距
  const updateMapViewportPadding = () => {
    Taro.nextTick(() => {
      const query = Taro.createSelectorQuery();
@@ -807,7 +809,13 @@
    orderStatusHandlerRef.current = (payload) => {
      const mappedTripStatus = payload?.tripStatus;
      if (typeof mappedTripStatus === 'number') {
        const currentLocalStatus = Number(Taro.getStorageSync('tripStatus'));
        // 如果本地状态已经比推送的状态新(状态递增原则),则忽略旧的推送消息
        if (currentLocalStatus > mappedTripStatus && currentLocalStatus !== 10) {
          return;
        }
        setTripStatus(mappedTripStatus);
        Taro.setStorageSync('tripStatus', mappedTripStatus);
      }
      // 车辆信息拉取:当收到有效的订单号时,在首次达到呼叫及后续阶段拉取车辆信息
      const incomingOrderId = payload?.content?.orderId || Taro.getStorageSync('orderId');
@@ -1455,6 +1463,8 @@
            electronicAreaId: res.xpElectronicFenceAreaId || '',
            time: res.endParkingTimeLimit || 0,
          };
          Taro.setStorageSync('tripStatus', mapOrderStatusToTripStatus(res.status || 1));
          setTripStatus(mapOrderStatusToTripStatus(res.status || 1));
          Taro.setStorageSync('startSite', nextStartSite);
          Taro.setStorageSync('endSite', nextEndSite);
          setStartSite(nextStartSite);
@@ -2102,7 +2112,10 @@
                tripStatus == 2 &&
                <ReleaseBeBeing
                  handleOpenCancelPopup={() => handleOpenCancelPopupByTripStatus(2)}
                  onFinish={() => setTripStatus(3)}
                  onFinish={() => {
                    setTripStatus(3);
                    Taro.setStorageSync('tripStatus', 3);
                  }}
                />
              }
              {/* 呼叫车辆弹窗 */}
src/robotaxi/pages/expense-description/index.tsx
@@ -2,6 +2,10 @@
import { useState, useEffect, useRef } from 'react';
import { View, Text, Image } from '@tarojs/components';
import { getFareBreakdown, FareBreakdownResponse, getFAQList, FAQItem } from '../../api/order';
import {
  formatTripDistance,
  formatTripDurationFromSeconds
} from '../../../utils/Robotaxi-public-method';
import EvaluatePopup from '../begin-route/components/evaluate-popup';
import './index.less';
import Subtract from '../../assets/Subtract.png';
@@ -116,7 +120,19 @@
          {fareData.start?.map((item, index) => (
            <View className='flex-between-card mb-16' key={index}>
              <View className='price-notice-label'>
                {item.startTime}-{item.endTime}({item.mileage}公里,{item.duration}分钟)
                {item.startTime}-{item.endTime}
                {
                  (item.mileage > 0 && item.duration > 0) &&
                  <Text>({formatTripDistance(item.mileage)},{formatTripDurationFromSeconds(item.duration)})</Text>
                }
                {
                  (item.mileage > 0 && !(item.duration > 0)) &&
                  <Text>({formatTripDistance(item.mileage)})</Text>
                }
                {
                  (!(item.mileage > 0) && item.duration > 0) &&
                  <Text>({formatTripDurationFromSeconds(item.duration)})</Text>
                }
              </View>
              <View className='price-notice-value'>{formatMoney(item.money)}元</View>
            </View>
@@ -129,7 +145,13 @@
          </View>
          {fareData.mileage?.map((item, index) => (
            <View className='flex-between-card mb-16' key={index}>
              <View className='price-notice-label'>{getTimeLabel(item.type)}({item.mileage}公里)</View>
              <View className='price-notice-label'>
                {getTimeLabel(item.type)}
                {
                  item.mileage > 0 &&
                  <Text>({formatTripDistance(item.mileage)})</Text>
                }
              </View>
              <View className='price-notice-value'>{formatMoney(item.money)}元</View>
            </View>
          ))}
@@ -141,7 +163,13 @@
          </View>
          {fareData.duration?.map((item, index) => (
            <View className='flex-between-card mb-16' key={index}>
              <View className='price-notice-label'>{getTimeLabel(item.type)}({item.duration}分钟)</View>
              <View className='price-notice-label'>
                {getTimeLabel(item.type)}
                {
                  item.duration > 0 &&
                  <Text>({formatTripDurationFromSeconds(item.duration)})</Text>
                }
              </View>
              <View className='price-notice-value'>{formatMoney(item.money)}元</View>
            </View>
          ))}
@@ -153,7 +181,13 @@
          </View>
          {fareData.longDistance?.map((item, index) => (
            <View className='flex-between-card mb-16' key={index}>
              <View className='price-notice-label'>{getTimeLabel(item.type)}({item.mileage}公里)</View>
              <View className='price-notice-label'>
                {getTimeLabel(item.type)}
                {
                  item.mileage > 0 &&
                  <Text>({formatTripDistance(item.mileage)})</Text>
                }
              </View>
              <View className='price-notice-value'>{formatMoney(item.money)}元</View>
            </View>
          ))}
src/robotaxi/pages/order/detail/index.tsx
@@ -99,6 +99,7 @@
  }
  const fetchOrderDetail = async (id: string) => {
    console.log('订单ID:', id);
    try {
      const res = await getOrderDetail(id);
      Taro.setNavigationBarTitle({ title: getNavTitle(res.status) || '订单详情' });
src/utils/Robotaxi-public-method.ts
@@ -379,14 +379,14 @@
          return itemName === normalizedCityName || item.name.includes(normalizedCityName) || normalizedCityName.includes(item.name);
        });
      }
      if (target) {
      cityId = target.id;
      // 修正返回的 code,确保使用的是系统匹配到的城市的标准 adcode
      if (target.adcode) {
        cityCode = target.adcode;
        cityId = target.id;
        // 修正返回的 code,确保使用的是系统匹配到的城市的标准 adcode
        if (target.adcode) {
          cityCode = target.adcode;
        }
      }
    }
    }
    return {
      name: cityName,
@@ -587,3 +587,29 @@
    }
  });
};
export const mapOrderStatusToTripStatus = (status: any) => {
  switch (Number(status)) {
    case 0:
      return 1;
    case 1:
      return 3;
    case 2:
    case 3:
      return 4;
    case 4:
      return 5;
    case 5:
    case 6:
      return 6;
    case 7:
      return 7;
    case 8:
      return 8;
    case 9:
    case 10:
      return 9;
    default:
      return 0;
  }
}