App Inventor 2 云数据库配置教程 - Firebase/CloudDB/自建后台

« 返回首页

App Inventor 2 云数据库配置教程 - Firebase/CloudDB/自建后台

在App Inventor 2中,如果你的应用需要在多台设备之间共享数据,或者需要将数据持久化存储在云端,就需要使用云数据库组件。本文将全面介绍App Inventor 2提供的云存储方案,并给出详细的配置步骤和实践代码。


一、云存储方案对比

App Inventor 2内置了多种云端数据存储组件,每种方案各有适用场景:

特性 CloudDB FirebaseDB TinyWebDB(自建后台) Google Spreadsheet
底层技术 Redis服务器 Google Firebase Realtime DB 自定义Web服务API Google Sheets API
默认服务器 MIT提供默认服务器 需自行配置Firebase项目 需自行搭建 需配置Google账户
实时同步 ✅ 支持DataChanged事件 ✅ 实时数据监听 ❌ 需手动轮询 ❌ 需手动轮询
数据共享 ✅ 多用户共享 ✅ 多用户共享 ✅ 多用户共享 ✅ 多用户共享
离线支持 ❌ 需联网 ✅ 本地缓存+同步 ❌ 需联网 ❌ 需联网
列表操作 ✅ 原子追加/移除 ✅ 支持 ❌ 需自行实现 ✅ 读写行列
安全规则 Token认证 Firebase Rules 自行实现 Google权限管理
适用场景 通用云端存储、实时协作 实时聊天、排行榜 完全自定义业务逻辑 数据报表、表单收集
难度 ⭐ 简单 ⭐⭐ 中等 ⭐⭐⭐ 较高 ⭐⭐ 中等
费用 MIT免费(有限额) Firebase免费额度 服务器自费 Google免费额度

二、CloudDB —— MIT官方云数据库

2.1 简介

CloudDB是App Inventor 2内置的非可视化组件,基于Redis服务器实现。它允许应用用户之间共享数据。默认情况下,数据存储在MIT维护的服务器上,你也可以搭建自己的Redis服务器。

核心特点:

  • 开箱即用,默认配置即可直接使用
  • 支持实时数据变更通知(DataChanged事件)
  • 原子性列表操作,多设备并发安全
  • 支持自建Redis服务器

2.2 配置步骤(使用MIT默认服务器)

步骤1:添加组件

在App Inventor 2设计视图中,从左侧组件面板的「Storage」分类中拖拽 CloudDB 组件到屏幕上。

步骤2:配置属性

属性 设置值 说明
RedisServer DEFAULT 使用MIT默认服务器
RedisPort 6381 默认端口,无需修改
Token 不修改 系统自动填充认证令牌
UseSSL true 默认服务器必须开启SSL
ProjectID 自动生成 每个项目唯一标识

提示: 使用MIT默认服务器时,所有属性保持默认即可,无需手动配置。

2.3 配置步骤(使用自建Redis服务器)

如果你需要完全掌控数据,可以搭建自己的Redis服务器:

步骤1:安装Redis

# Ubuntu/Debian
sudo apt update
sudo apt install redis-server

# CentOS
sudo yum install redis

# Docker方式(推荐)
docker run -d --name redis-clouddb \
  -p 6381:6379 \
  -v redis-data:/data \
  redis:7 redis-server --appendonly yes --requirepass your_password_here

步骤2:配置Redis

编辑Redis配置文件(通常为 /etc/redis/redis.conf):

# 设置监听端口
port 6381

# 设置密码
requirepass your_secure_password

# 开启持久化
appendonly yes
appendfilename "appendonly.aof"

# 绑定地址(根据需要调整)
bind 0.0.0.0

步骤3:在App Inventor中配置

属性 设置值 说明
RedisServer 你的服务器IP或域名 192.168.1.100redis.example.com
RedisPort 6381 与服务器端口一致
Token your_secure_password Redis服务器密码
UseSSL 根据服务器配置 如果服务器启用了SSL则为true
ProjectID 自定义 多项目可使用不同ProjectID隔离数据

2.4 数据读写积木块操作

存储数据

调用 CloudDB.StoreValue(
    tag: "userName",
    valueToStore: "张三"
)

当存储完成后,会触发 CloudDB.UpdateDone(tag, operation) 事件。

读取数据

调用 CloudDB.GetValue(
    tag: "userName",
    valueIfTagNotThere: ""
)

事件 CloudDB.GotValue(tag, value):
    如果 tag = "userName":
        设置 Label1.文本 为 value

注意: GetValue 是异步操作,不会直接返回值。你必须在 GotValue 事件中处理返回的数据。

监听数据变化

事件 CloudDB.DataChanged(tag, value):
    // 当任何设备修改了数据,所有连接的设备都会收到此事件
    设置 Label_Status.文本 为 合并文本("数据已更新:", tag, " = ", value)

列表操作

// 原子性追加元素到列表(多设备并发安全)
调用 CloudDB.AppendValueToList(
    tag: "chatMessages",
    itemToAdd: "你好!"
)

// 原子性获取并移除列表首元素(适合消息队列)
调用 CloudDB.RemoveFirstFromList(tag: "taskQueue")

事件 CloudDB.FirstRemoved(value):
    设置 Label_Result.文本 为 合并文本("取出:", value)

获取所有标签

调用 CloudDB.GetTagList()

事件 CloudDB.TagList(value):
    // value 是所有标签名的列表
    设置 ListPicker1.元素 为 value

删除数据

// 删除指定标签的数据
调用 CloudDB.ClearTag(tag: "userName")

// 检查连接状态
设置 Label_Status.文本 为 CloudDB.CloudConnected()

2.5 完整示例:简易聊天应用

界面设计:

  • TextBox_Chat:输入聊天消息
  • Button_Send:发送按钮
  • Label_Messages:显示聊天记录

积木块逻辑:

// Screen初始化
事件 Screen1.初始化():
    调用 CloudDB.GetValue(tag: "chatHistory", valueIfTagNotThere: 空列表)

// 发送消息
事件 Button_Send.点击():
    调用 CloudDB.AppendValueToList(
        tag: "chatHistory",
        itemToAdd: 合并文本(TextBox_Chat.文本)
    )
    设置 TextBox_Chat.文本 为 ""

// 收到历史消息
事件 CloudDB.GotValue(tag, value):
    如果 tag = "chatHistory":
        设置 Label_Messages.文本 为 合并文本列表(value, "\n")

// 实时监听新消息
事件 CloudDB.DataChanged(tag, value):
    如果 tag = "chatHistory":
        设置 Label_Messages.文本 为 合并文本列表(value, "\n")

三、FirebaseDB —— Google实时数据库

3.1 简介

FirebaseDB组件对接Google Firebase Realtime Database,提供实时数据同步能力。数据以JSON树形结构存储,支持离线缓存和自动同步。

核心特点:

  • Google级别的稳定性和扩展性
  • 真正的实时数据同步
  • 离线缓存,网络恢复后自动同步
  • 丰富的安全规则配置
  • 免费额度充足(Spark计划)

3.2 Firebase项目创建

步骤1:注册Firebase

  1. 访问 Firebase控制台
  2. 使用Google账户登录
  3. 点击「添加项目」
  4. 输入项目名称(如 my-appinventor-app
  5. 选择是否启用Google Analytics(可选)
  6. 点击「创建项目」

步骤2:创建Realtime Database

  1. 在Firebase控制台左侧菜单中找到「Build」→「Realtime Database」
  2. 点击「Create Database」
  3. 选择数据库位置(建议选择离用户最近的区域)
  4. 选择安全规则模式:
    • 测试模式:允许所有读写(开发阶段使用)
    • 锁定模式:拒绝所有读写(生产环境推荐)

步骤3:获取配置信息

在Firebase项目设置中记录以下信息:

  • 数据库URL:格式为 https://your-project-id-default-rtdb.firebaseio.com/
  • Firebase Token:在Realtime Database的规则中配置

3.3 在App Inventor中配置FirebaseDB

步骤1:添加组件

在设计视图中,从「Storage」分类拖拽 FirebaseDB 组件到屏幕。

步骤2:配置属性

属性 设置值 说明
FirebaseToken 从Firebase获取的Token 项目设置中的Web API Key
FirebaseURL 数据库URL https://xxx.firebaseio.com/
UseService false 使用Token认证方式

3.4 Firebase安全规则配置

在Firebase控制台的「Realtime Database」→「Rules」中配置安全规则:

开发/测试阶段规则(允许所有读写):

{
  "rules": {
    ".read": true,
    ".write": true
  }
}

生产环境推荐规则(需要认证):

{
  "rules": {
    "users": {
      "$uid": {
        ".read": "$uid === auth.uid",
        ".write": "$uid === auth.uid"
      }
    },
    "public": {
      ".read": true,
      ".write": "auth !== null"
    }
  }
}

⚠️ 安全警告: 测试模式规则会在30天后自动过期。生产环境务必配置适当的安全规则,避免数据泄露。

3.5 数据读写积木块操作

存储数据

调用 FirebaseDB.StoreValue(
    tag: "score",
    valueToStore: 100
)

事件 FirebaseDB.DataChanged(tag, value):
    // 数据存储成功或变更时触发

读取数据

调用 FirebaseDB.GetValue(
    tag: "score",
    valueIfTagNotThere: 0
)

事件 FirebaseDB.GotValue(tag, value):
    如果 tag = "score":
        设置 Label_Score.文本 为 合并文本("分数:", value)

删除数据

调用 FirebaseDB.ClearTag(tag: "score")

追加到列表

调用 FirebaseDB.AppendValueToList(
    tag: "messages",
    itemToAdd: "新消息"
)

移除列表首元素

调用 FirebaseDB.RemoveFirstFromList(tag: "taskQueue")

事件 FirebaseDB.FirstRemoved(value):
    设置 Label_Result.文本 为 value

3.6 完整示例:实时排行榜

界面设计:

  • TextBox_Name:输入玩家名
  • TextBox_Score:输入分数
  • Button_Submit:提交按钮
  • Label_Leaderboard:显示排行榜

积木块逻辑:

// 初始化加载排行榜
事件 Screen1.初始化():
    调用 FirebaseDB.GetValue(tag: "leaderboard", valueIfTagNotThere: 空列表)

// 提交分数
事件 Button_Submit.点击():
    定义局部变量 entry = 合并文本(TextBox_Name.文本, ":", TextBox_Score.文本)
    调用 FirebaseDB.AppendValueToList(
        tag: "leaderboard",
        itemToAdd: entry
    )

// 收到数据
事件 FirebaseDB.GotValue(tag, value):
    如果 tag = "leaderboard":
        设置 Label_Leaderboard.文本 为 合并文本列表(value, "\n")

// 实时更新
事件 FirebaseDB.DataChanged(tag, value):
    如果 tag = "leaderboard":
        设置 Label_Leaderboard.文本 为 合并文本列表(value, "\n")

四、TinyWebDB —— 自建网络微数据库后台

4.1 简介

TinyWebDB是App Inventor 2中最灵活的云存储方案。它不绑定特定的云服务商,而是通过HTTP接口与你自己搭建的Web服务器通信。你可以使用PHP、Node.js、Python等任何后端技术来实现服务接口。

核心特点:

  • 完全自主可控,数据存储在自己的服务器
  • 可以使用MySQL、SQLite、MongoDB等任何数据库
  • 可以实现复杂的业务逻辑(用户认证、数据过滤等)
  • 可以部署在国内服务器(阿里云、腾讯云等),访问速度快
  • 支持PHP、Node.js、Python、Java等后端技术

4.2 TinyWebDB API规范

TinyWebDB组件与后台服务之间通过标准HTTP POST请求通信,使用特定的JSON格式:

保存数据(storeavalue)

请求:

POST /api/storeavalue
Content-Type: application/x-www-form-urlencoded

tag=userName&value=张三

成功响应:

["STORED", "userName", "张三"]

获取数据(getvalue)

请求:

POST /api/getvalue
Content-Type: application/x-www-form-urlencoded

tag=userName

成功响应(数据存在):

["VALUE", "userName", "张三"]

成功响应(数据不存在):

["VALUE", "userName", ""]

4.3 在App Inventor中配置TinyWebDB

步骤1:添加组件

在设计视图中,从「Storage」分类拖拽 TinyWebDB 组件到屏幕。

步骤2:配置属性

属性 设置值 说明
ServiceURL http://你的服务器地址/api/ 你的后台服务URL

注意: ServiceURL必须以 / 结尾。如果使用HTTPS,确保服务器SSL证书有效。

4.4 PHP后台实现方案

方案一:基于文件的简易存储

以下PHP代码使用JSON文件存储数据,适合小型应用:

文件结构:

/var/www/html/tinywebdb/
├── api/
│   ├── index.php      # API入口
│   └── data/
│       └── store.json # 数据文件

api/index.php:

<?php
/**
 * TinyWebDB API - 文件存储版
 * 适用于小型应用,无需数据库
 */

header('Content-Type: application/json');
header('Access-Control-Allow-Origin: *');

$dataFile = __DIR__ . '/data/store.json';

// 确保数据目录存在
if (!is_dir(__DIR__ . '/data')) {
    mkdir(__DIR__ . '/data', 0755, true);
}

// 读取现有数据
function loadData($file) {
    if (file_exists($file)) {
        $content = file_get_contents($file);
        return json_decode($content, true) ?: [];
    }
    return [];
}

// 保存数据
function saveData($file, $data) {
    file_put_contents($file, json_encode($data, JSON_UNESCAPED_UNICODE | JSON_PRETTY_PRINT));
}

// 获取POST参数
$tag = isset($_POST['tag']) ? $_POST['tag'] : '';
$value = isset($_POST['value']) ? $_POST['value'] : '';

// 路由处理
$action = basename($_SERVER['REQUEST_URI']);

if ($action === 'storeavalue') {
    // 保存数据
    if (empty($tag)) {
        echo json_encode(["ERROR", "Tag cannot be empty"]);
        exit;
    }

    $data = loadData($dataFile);
    $data[$tag] = $value;
    saveData($dataFile, $data);

    echo json_encode(["STORED", $tag, $value]);

} elseif ($action === 'getvalue') {
    // 获取数据
    if (empty($tag)) {
        echo json_encode(["ERROR", "Tag cannot be empty"]);
        exit;
    }

    $data = loadData($dataFile);
    $resultValue = isset($data[$tag]) ? $data[$tag] : "";

    echo json_encode(["VALUE", $tag, $resultValue]);

} else {
    echo json_encode(["ERROR", "Unknown action: $action"]);
}
?>

方案二:基于MySQL的完整方案

适合生产环境,支持高并发:

数据库初始化(SQL):

CREATE DATABASE IF NOT EXISTS tinywebdb
  DEFAULT CHARACTER SET utf8mb4
  DEFAULT COLLATE utf8mb4_unicode_ci;

USE tinywebdb;

CREATE TABLE IF NOT EXISTS store (
    id INT AUTO_INCREMENT PRIMARY KEY,
    tag VARCHAR(255) NOT NULL,
    value TEXT,
    created_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP,
    updated_at TIMESTAMP DEFAULT CURRENT_TIMESTAMP ON UPDATE CURRENT_TIMESTAMP,
    UNIQUE KEY idx_tag (tag)
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4;

api/index.php:

<?php
/**
 * TinyWebDB API - MySQL存储版
 * 适用于生产环境
 */

header('Content-Type: application/json');
header('Access-Control-Allow-Origin: *');

// 数据库配置
$dbHost = 'localhost';
$dbName = 'tinywebdb';
$dbUser = 'tinywebdb_user';
$dbPass = 'your_secure_password';

// 可选:简易API密钥认证
$apiKey = 'your_api_key_here';
$enableAuth = false; // 设为 true 启用认证

// 认证检查
if ($enableAuth) {
    $requestKey = isset($_SERVER['HTTP_X_API_KEY']) ? $_SERVER['HTTP_X_API_KEY'] : '';
    if ($requestKey !== $apiKey) {
        http_response_code(401);
        echo json_encode(["ERROR", "Unauthorized"]);
        exit;
    }
}

// 数据库连接
try {
    $pdo = new PDO(
        "mysql:host=$dbHost;dbname=$dbName;charset=utf8mb4",
        $dbUser,
        $dbPass,
        [PDO::ATTR_ERRMODE => PDO::ERRMODE_EXCEPTION]
    );
} catch (PDOException $e) {
    echo json_encode(["ERROR", "Database connection failed"]);
    exit;
}

// 获取POST参数
$tag = isset($_POST['tag']) ? $_POST['tag'] : '';
$value = isset($_POST['value']) ? $_POST['value'] : '';

// 路由处理
$action = basename($_SERVER['REQUEST_URI']);

if ($action === 'storeavalue') {
    if (empty($tag)) {
        echo json_encode(["ERROR", "Tag cannot be empty"]);
        exit;
    }

    // 使用 INSERT ... ON DUPLICATE KEY UPDATE 实现 upsert
    $stmt = $pdo->prepare(
        "INSERT INTO store (tag, value) VALUES (:tag, :value)
         ON DUPLICATE KEY UPDATE value = :value2, updated_at = NOW()"
    );
    $stmt->execute([
        ':tag'   => $tag,
        ':value' => $value,
        ':value2'=> $value
    ]);

    echo json_encode(["STORED", $tag, $value]);

} elseif ($action === 'getvalue') {
    if (empty($tag)) {
        echo json_encode(["ERROR", "Tag cannot be empty"]);
        exit;
    }

    $stmt = $pdo->prepare("SELECT value FROM store WHERE tag = :tag");
    $stmt->execute([':tag' => $tag]);
    $row = $stmt->fetch(PDO::FETCH_ASSOC);

    $resultValue = $row ? $row['value'] : "";
    echo json_encode(["VALUE", $tag, $resultValue]);

} else {
    echo json_encode(["ERROR", "Unknown action: $action"]);
}
?>

4.5 Node.js后台实现方案

如果你更习惯使用Node.js,以下是等效的后台实现:

安装依赖:

mkdir tinywebdb-server && cd tinywebdb-server
npm init -y
npm install express body-parser

server.js:

/**
 * TinyWebDB API - Node.js实现
 * 使用文件存储(可替换为MongoDB/MySQL)
 */

const express = require('express');
const bodyParser = require('body-parser');
const fs = require('fs');
const path = require('path');

const app = express();
const PORT = process.env.PORT || 3000;
const DATA_FILE = path.join(__dirname, 'data', 'store.json');

// 中间件
app.use(bodyParser.urlencoded({ extended: true }));
app.use(bodyParser.json());

// CORS支持
app.use((req, res, next) => {
    res.header('Access-Control-Allow-Origin', '*');
    res.header('Access-Control-Allow-Methods', 'GET, POST');
    res.header('Access-Control-Allow-Headers', 'Content-Type');
    next();
});

// 确保数据目录和文件存在
function ensureDataFile() {
    const dir = path.dirname(DATA_FILE);
    if (!fs.existsSync(dir)) {
        fs.mkdirSync(dir, { recursive: true });
    }
    if (!fs.existsSync(DATA_FILE)) {
        fs.writeFileSync(DATA_FILE, '{}', 'utf8');
    }
}

// 读取数据
function loadData() {
    ensureDataFile();
    const content = fs.readFileSync(DATA_FILE, 'utf8');
    return JSON.parse(content);
}

// 保存数据
function saveData(data) {
    ensureDataFile();
    fs.writeFileSync(DATA_FILE, JSON.stringify(data, null, 2), 'utf8');
}

// 保存数据API
app.post('/api/storeavalue', (req, res) => {
    const tag = req.body.tag || '';
    const value = req.body.value || '';

    if (!tag) {
        return res.json(['ERROR', 'Tag cannot be empty']);
    }

    const data = loadData();
    data[tag] = value;
    saveData(data);

    res.json(['STORED', tag, value]);
});

// 获取数据API
app.post('/api/getvalue', (req, res) => {
    const tag = req.body.tag || '';

    if (!tag) {
        return res.json(['ERROR', 'Tag cannot be empty']);
    }

    const data = loadData();
    const resultValue = data.hasOwnProperty(tag) ? data[tag] : '';

    res.json(['VALUE', tag, resultValue]);
});

// 启动服务器
app.listen(PORT, () => {
    console.log(`TinyWebDB Server running on http://localhost:${PORT}`);
    console.log(`API endpoints:`);
    console.log(`  POST http://localhost:${PORT}/api/storeavalue`);
    console.log(`  POST http://localhost:${PORT}/api/getvalue`);
});

启动服务器:

node server.js
# 或使用 pm2 保持后台运行
npm install -g pm2
pm2 start server.js --name tinywebdb

然后在App Inventor的TinyWebDB组件中设置:

ServiceURL = http://你的服务器IP:3000/api/

4.6 TinyWebDB数据读写积木块操作

存储数据

调用 TinyWebDB.StoreValue(
    tag: "userName",
    valueToStore: "张三"
)

事件 TinyWebDB.ValueStored():
    // 数据存储成功
    设置 Label_Status.文本 为 "保存成功"

读取数据

调用 TinyWebDB.GetValue(tag: "userName")

事件 TinyWebDB.GotValue(tag, valueFromWebDB):
    如果 tag = "userName":
        设置 Label_Name.文本 为 valueFromWebDB

注意: 与CloudDB/FirebaseDB类似,GetValue 是异步操作,必须在 GotValue 事件中处理返回数据。

错误处理

事件 TinyWebDB.WebServiceError(message):
    设置 Label_Error.文本 为 合并文本("网络错误:", message)

4.7 完整示例:用户登录注册系统

界面设计:

  • TextBox_Username:用户名输入
  • TextBox_Password:密码输入
  • Button_Register:注册按钮
  • Button_Login:登录按钮
  • Label_Status:状态提示

积木块逻辑:

// 注册
事件 Button_Register.点击():
    如果 TextBox_Username.文本 = "" 或 TextBox_Password.文本 = "":
        设置 Label_Status.文本 为 "用户名和密码不能为空"
    否则:
        // 先检查用户是否已存在
        调用 TinyWebDB.GetValue(
            tag: 合并文本("user:", TextBox_Username.文本)
        )

// 读取结果
事件 TinyWebDB.GotValue(tag, valueFromWebDB):
    如果 包含文本(tag, "user:"):
        如果 valueFromWebDB = "":
            // 用户不存在,可以注册
            调用 TinyWebDB.StoreValue(
                tag: 合并文本("user:", TextBox_Username.文本),
                valueToStore: TextBox_Password.文本
            )
            设置 Label_Status.文本 为 "注册成功!"
        否则:
            // 用于登录验证
            如果 valueFromWebDB = TextBox_Password.文本:
                设置 Label_Status.文本 为 "登录成功!"
            否则:
                设置 Label_Status.文本 为 "密码错误"

// 登录
事件 Button_Login.点击():
    调用 TinyWebDB.GetValue(
        tag: 合并文本("user:", TextBox_Username.文本)
    )

五、Web组件 —— 通用HTTP数据交互

除了以上专门的数据库组件,App Inventor 2还提供了 Web 组件,可以与任何HTTP API进行数据交互,适合与自建PHP/Node.js服务器进行复杂数据交换。

5.1 发送GET请求

// 设置请求URL
设置 Web1.Url 为 "http://你的服务器/api/getData.php?key=value"
调用 Web1.执行GET请求()

事件 Web1.收到文本(responseCode, responseContent):
    如果 responseCode = 200:
        设置 Label_Result.文本 为 responseContent

5.2 发送POST请求

// 设置请求URL和参数
设置 Web1.Url 为 "http://你的服务器/api/saveData.php"
调用 Web1.执行POST请求(
    文本: 合并文本("name=", TextBox_Name.文本, "&score=", TextBox_Score.文本),
    编码: "UTF-8"
)

事件 Web1.收到文本(responseCode, responseContent):
    如果 responseCode = 200:
        设置 Label_Status.文本 为 "提交成功"

5.3 PHP后台接收示例

<?php
header('Content-Type: application/json; charset=utf-8');
header('Access-Control-Allow-Origin: *');

$method = $_SERVER['REQUEST_METHOD'];

if ($method === 'GET') {
    $key = isset($_GET['key']) ? $_GET['key'] : '';
    // 处理GET请求,查询数据
    $result = ["status" => "ok", "data" => "查询结果"];
    echo json_encode($result, JSON_UNESCAPED_UNICODE);

} elseif ($method === 'POST') {
    $name = isset($_POST['name']) ? $_POST['name'] : '';
    $score = isset($_POST['score']) ? $_POST['score'] : '';
    // 处理POST请求,保存数据
    $result = ["status" => "ok", "message" => "保存成功"];
    echo json_encode($result, JSON_UNESCAPED_UNICODE);
}
?>

六、安全最佳实践

6.1 数据传输安全

措施 说明
使用HTTPS 生产环境务必启用SSL证书(Let’s Encrypt免费获取)
API密钥认证 自建后台应实现API Key验证
输入验证 后台必须验证和过滤所有输入数据
速率限制 防止恶意请求,建议每IP每分钟限制请求数

6.2 Firebase安全规则进阶

{
  "rules": {
    // 公开只读数据
    "public": {
      ".read": true,
      ".write": false
    },
    // 已认证用户可读写
    "users": {
      "$uid": {
        ".read": "auth != null && auth.uid == $uid",
        ".write": "auth != null && auth.uid == $uid"
      }
    },
    // 限流:每分钟最多10次写入
    "messages": {
      ".read": true,
      ".write": "auth != null && newData.exists()",
      "$messageId": {
        ".validate": "newData.hasChildren(['text', 'timestamp'])"
      }
    }
  }
}

6.3 自建后台安全加固

Nginx反向代理配置示例:

server {
    listen 443 ssl http2;
    server_name api.example.com;

    ssl_certificate /etc/letsencrypt/live/api.example.com/fullchain.pem;
    ssl_certificate_key /etc/letsencrypt/live/api.example.com/privkey.pem;

    # 限流
    limit_req_zone $binary_remote_addr zone=api:10m rate=30r/m;

    location /api/ {
        limit_req zone=api burst=10 nodelay;
        proxy_pass http://127.0.0.1:3000;
        proxy_set_header Host $host;
        proxy_set_header X-Real-IP $remote_addr;
    }
}

七、方案选择建议

根据不同的应用场景,推荐以下选择策略:

场景 推荐方案 理由
快速原型开发 CloudDB(MIT默认) 零配置,开箱即用
教学演示 CloudDB(MIT默认) 无需额外搭建,适合课堂教学
实时聊天/协作 FirebaseDB 原生实时同步,离线支持
排行榜/成绩统计 CloudDB 或 FirebaseDB 原子操作保证并发安全
国内用户为主 TinyWebDB自建后台 部署在国内服务器,访问速度快
需要复杂业务逻辑 TinyWebDB + Web组件 完全自定义后台逻辑
数据报表/表单 Google Spreadsheet 天然支持表格操作
企业级应用 TinyWebDB + 自建后台 数据安全可控,符合合规要求

八、常见问题(FAQ)

Q1:CloudDB的MIT默认服务器有容量限制吗?

MIT默认服务器是共享资源,适合开发和测试。对于生产环境或高并发应用,建议自建Redis服务器。

Q2:Firebase在国内能正常访问吗?

Firebase服务在国内访问可能不稳定。如果目标用户在国内,建议使用CloudDB(自建Redis)或TinyWebDB(自建后台)方案。

Q3:TinyWebDB的ServiceURL可以配置多个吗?

每个TinyWebDB组件只能配置一个ServiceURL。如果需要连接多个服务,可以添加多个TinyWebDB组件。

Q4:如何在不同应用之间共享CloudDB数据?

CloudDB的数据隔离基于ProjectID。要跨应用共享数据,可以使用相同的Token值。将一个应用的Token复制到另一个应用的CloudDB组件中即可实现数据共享。

Q5:自建后台可以用云服务器吗?

可以。阿里云ECS、腾讯云CVM、华为云ECS等国内云服务器都可以部署TinyWebDB后台。推荐使用Ubuntu系统,搭配Nginx反向代理和Let’s Encrypt免费SSL证书。


九、参考资源


© 2024 App Inventor 2 中文网。本文基于MIT官方文档编写,仅供学习参考。

« 返回首页

文档反馈