You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

FlutterFlow自定义函数测试正常,移动端正式构建失效求助

问题描述

我在FlutterFlow中编写了Dart自定义函数,功能是当Firebase内指定documentId的用户Point数据达到50、100、150等阈值时,将其Balance数据增加15。函数在FlutterFlow测试模式下运行正常,但通过Codemagic提交至App Store、Google Play后,TestFlight及正式应用中无法正常执行(Balance未按预期增加15)。

我尝试将逻辑整合到另一个测试/正式构建均正常的函数中,问题依旧存在。

原函数代码:

import '/backend/backend.dart';
import '/flutter_flow/flutter_flow_theme.dart';
import '/flutter_flow/flutter_flow_util.dart';
import '/custom_code/actions/index.dart'; 
import '/flutter_flow/custom_functions.dart'; 
import 'package:flutter/material.dart';
import 'package:cloud_firestore/cloud_firestore.dart';

Future<void> updateBalanceAndPointPremium(String documentId) async {
  try {
    final DocumentReference userDocRef =
        FirebaseFirestore.instance.collection('users').doc(documentId);

    final DocumentSnapshot snapshot = await userDocRef.get();
    if (snapshot.exists) {
      final data = snapshot.data() as Map<String, dynamic>;
      final double point = data['Point'] ?? 0.0;
      final double balance = data['Balance'] ?? 0.0;
      final int balanceTimes = data['balanceConvertTimes'] ?? 0;

      double updatedBalance = balance;
      int updatedBalanceTimes = balanceTimes;

      // Calculate the number of times the balance should be increased by 15
      int increaseCount = ((point ~/ 50) - balanceTimes);

      if (increaseCount > 0) {
        updatedBalance += increaseCount * 15;
        updatedBalanceTimes += increaseCount;
      }

      final updateData = {
        'Balance': updatedBalance,
        'balanceConvertTimes': updatedBalanceTimes
      };

      await userDocRef.update(updateData);
      print('Balance field updated successfully!');
    }
  } catch (e) {
    print('Error updating balance field: $e');
  }
}

整合后的函数代码:

import '/backend/backend.dart';
import '/flutter_flow/flutter_flow_theme.dart';
import '/flutter_flow/flutter_flow_util.dart';
import '/custom_code/actions/index.dart'; // Imports other custom actions
import '/flutter_flow/custom_functions.dart'; // Imports custom functions
import 'package:flutter/material.dart';
import 'package:cloud_firestore/cloud_firestore.dart';

Future<void> addPointandBalancePremium(
    String documentId, double amountToAdd) async {
  try {
    final DocumentReference userDocRef =
        FirebaseFirestore.instance.collection('users').doc(documentId);

    await FirebaseFirestore.instance.runTransaction((transaction) async {
      final DocumentSnapshot snapshot = await transaction.get(userDocRef);
      if (snapshot.exists) {
        final data = snapshot.data() as Map<String, dynamic>;
        final currentAmount = data['Point'] ?? 0.0;

        final double balance = data['Balance'] ?? 0.0;
        final int balanceTimes = data['balanceConvertTimes'] ?? 0;

        double updatedBalance = balance;
        int updatedBalanceTimes = balanceTimes;

        var currentDist = data['pointToNextReward'] ?? 0.0;
        var currentDistFree = data['pointToNextRewardFree'] ?? 0.0;
        final newAmount = currentAmount + (0.2 * amountToAdd / 100);
        var newDist = 50 - (0.2 * amountToAdd / 100 - currentDist);
        var newDistFree = 100 - (0.2 * amountToAdd / 100 - currentDistFree);

        int increaseCount = ((newAmount ~/ 50) - balanceTimes);

        if (increaseCount > 0) {
          updatedBalance += increaseCount * 15;
          updatedBalanceTimes += increaseCount;
        }

        currentDist = newDist;
        if (newDist >= 50) {
          currentDist = newDist - 50;
        }
        ;

        currentDistFree = newDistFree;
        if (newDistFree >= 100) {
          currentDistFree = newDistFree - 100;
        }
        ;

        transaction.update(userDocRef, {
          'Point': newAmount,
          'pointToNextReward': currentDist,
          'pointToNextRewardFree': currentDistFree,
          'Balance': updatedBalance,
          'balanceConvertTimes': updatedBalanceTimes
        });
      }
    });

    print('Point and Balance fields updated successfully!');
  } catch (e) {
    print('Error updating Point field: $e');
  }
}
排查与解决方案

1. 检查Firebase生产环境安全规则

测试模式下FlutterFlow通常使用宽松的Firestore规则,但生产环境可能限制了写权限。确保users集合的更新权限符合业务需求,例如:

rules_version = '2';
service cloud.firestore {
  match /databases/{database}/documents {
    match /users/{userId} {
      allow update: if request.auth != null && request.auth.uid == userId;
      // 根据你的业务场景调整,比如允许管理员更新等
    }
  }
}

2. 修复浮点运算精度问题

代码中使用~/(整数除法)处理double类型的newAmount,生产环境可能因浮点精度误差导致increaseCount计算错误。建议先将浮点值转为整数或使用精确的取整方式:

// 替换原increaseCount计算逻辑
int increaseCount = ((newAmount.round() ~/ 50) - balanceTimes);
// 或者使用floor确保向下取整(符合阈值判断逻辑)
int increaseCount = ((newAmount.floor() ~/ 50) - balanceTimes);

3. 使用FlutterFlow提供的Firestore实例

FlutterFlow导出的项目中,应使用Backend.instance.firestore而非直接调用FirebaseFirestore.instance,避免生产环境配置差异导致实例异常:

// 替换原Firestore实例引用
final DocumentReference userDocRef =
    Backend.instance.firestore.collection('users').doc(documentId);

// 事务部分也同步替换
await Backend.instance.firestore.runTransaction((transaction) async {
  // ... 原有逻辑
});

4. 添加生产环境可追踪的日志

生产环境中print日志无法查看,需集成Firebase Crashlytics或使用debugPrint(需确保生产环境开启日志):

import 'package:firebase_crashlytics/firebase_crashlytics.dart';

// ... 函数代码

catch (e, stackTrace) {
  FirebaseCrashlytics.instance.recordError(e, stackTrace);
  debugPrint('Update failed: $e');
}

5. 验证事务内的逻辑正确性

检查newDist和newDistFree的计算逻辑是否存在错误,例如:

// 原newDist计算可能存在逻辑问题,可调整为更清晰的写法
final addedPoints = 0.2 * amountToAdd / 100;
final newAmount = currentAmount + addedPoints;
var newDist = currentDist + addedPoints;
if (newDist >= 50) {
  newDist -= 50;
}
// newDistFree同理
var newDistFree = currentDistFree + addedPoints;
if (newDistFree >= 100) {
  newDistFree -= 100;
}

6. 确认Codemagic构建配置

确保Codemagic的构建脚本没有排除custom_code目录的代码,FlutterFlow导出的自定义函数都存放在该目录,需保证构建时正确编译。


内容的提问来源于stack exchange,提问作者Andrew Nguyen

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.07.16 07:23:08