Flutter数据库连接插件mssql_connection的使用

发布于 1周前 作者 wuwangju 来自 Flutter

Flutter数据库连接插件mssql_connection的使用

MSSQL Connection Plugin

mssql_connection 插件允许Flutter应用程序无缝连接到并交互Microsoft SQL Server数据库,提供丰富的查询和数据操作功能。

🚀 现在支持 Windows 和 Android 的跨平台开发。您可以轻松自定义数据库操作,确保安全连接,并简化应用开发。 🔗


功能特性

  • 🔄 跨平台支持: 为Android和Windows提供无缝的Microsoft SQL Server集成。
  • 📊 查询执行: 轻松执行SQL查询并以JSON格式检索数据。
  • 可配置超时: 设置连接超时以确保安全可靠的操作。
  • 🧩 简化的API: 面向Flutter应用的开发者友好API。
  • 🔄 自动重连: 在中断期间进行强大的连接处理。
  • 🚀 轻松的数据写入: 支持事务的插入、更新和删除操作。

安装

要将MsSQL Connection插件添加到您的Flutter项目中,请遵循以下简单步骤:

  1. 添加依赖: 打开 pubspec.yaml 文件并添加以下内容:

    dependencies:
      mssql_connection: ^2.0.0
    

    ^2.0.0 替换为最新版本。

  2. 安装包: 运行以下命令来获取插件:

    flutter pub get
    
  3. 导入插件: 在Dart代码中包含插件:

    import 'package:mssql_connection/mssql_connection.dart';
    
  4. 初始化连接: 获取 MssqlConnection 实例:

    MssqlConnection mssqlConnection = MssqlConnection.getInstance();
    

使用示例

连接到数据库

使用 connect 方法与Microsoft SQL Server建立连接,该方法带有可定制参数:

bool isConnected = await mssqlConnection.connect(
  ip: 'your_server_ip',
  port: 'your_server_port',
  databaseName: 'your_database_name',
  username: 'your_username',
  password: 'your_password',
  timeoutInSeconds: 15,
);

// `isConnected` 返回true表示连接已建立。

获取数据

使用 getData 方法从数据库中获取数据:

String query = 'SELECT * FROM your_table';
String result = await mssqlConnection.getData(query);

// `result` 包含JSON格式的数据。

写入数据

使用 writeData 方法执行插入、更新或删除操作:

String query = 'UPDATE your_table SET column_name = "new_value" WHERE condition';
String result = await mssqlConnection.writeData(query);

// `result` 包含关于操作的详细信息,例如受影响的行数。

断开连接

当不再需要数据库连接时,关闭它:

bool isDisconnected = await mssqlConnection.disconnect();

// `isDisconnected` 返回true表示连接成功关闭。

示例应用代码

下面是一个完整的Flutter应用程序示例,展示了如何使用 mssql_connection 插件连接到SQL Server,执行读取和写入操作:

import 'dart:convert';

import 'package:flutter/material.dart';
import 'package:flutter/services.dart';
import 'package:mssql_connection/mssql_connection.dart';

void main() {
  runApp(const MyApp());
}

class MyApp extends StatefulWidget {
  const MyApp({super.key});

  @override
  State<MyApp> createState() => _MyAppState();
}

class _MyAppState extends State<MyApp> {
  @override
  void initState() {
    super.initState();
  }

  @override
  Widget build(BuildContext context) {
    return const MaterialApp(
        debugShowCheckedModeBanner: false, home: HomPage());
  }
}

const textStyle = TextStyle(fontSize: 18);

class HomPage extends StatefulWidget {
  const HomPage({super.key});

  @override
  State<HomPage> createState() => _HomPageState();
}

class _HomPageState extends State<HomPage> {
  String ip = '',
      port = '',
      username = '',
      password = '',
      databaseName = '',
      readQuery = '',
      writeQuery = '';
  final _sqlConnection = MssqlConnection.getInstance();
  final pageController = PageController();

  @override
  Widget build(BuildContext context) {
    return Scaffold(
      appBar: AppBar(
        title: const Text('SQL Connection Example'),
      ),
      body: PageView(
        controller: pageController,
        children: [
          SingleChildScrollView(
            child: Padding(
              padding: const EdgeInsets.all(10.0),
              child: Column(children: [
                Row(children: [
                  Flexible(
                      child: customTextField("IP address",
                          onchanged: (p0) => ip = p0,
                          keyboardType: TextInputType.number)),
                  const SizedBox(width: 10),
                  Flexible(
                      child: customTextField("Port",
                          onchanged: (p0) => port = p0,
                          keyboardType: TextInputType.number))
                ]),
                customTextField("Database Name",
                    onchanged: (p0) => databaseName = p0),
                customTextField("Username", onchanged: (p0) => username = p0),
                customTextField("Password", onchanged: (p0) => password = p0),
                const SizedBox(height: 15.0),
                FloatingActionButton.extended(
                    onPressed: connect, label: const Text("Connect"))
              ]),
            ),
          ),
          SingleChildScrollView(
            child: Padding(
              padding: const EdgeInsets.all(10.0),
              child: Column(
                children: [
                  Card(
                    child: Padding(
                      padding: const EdgeInsets.all(10.0),
                      child: Column(
                        crossAxisAlignment: CrossAxisAlignment.start,
                        children: [
                          Row(
                            mainAxisAlignment: MainAxisAlignment.spaceBetween,
                            children: [
                              const Text("Read Data", style: textStyle),
                              IconButton(
                                  onPressed: () => execute("Read", context),
                                  icon: const Icon(Icons.play_arrow_rounded))
                            ],
                          ),
                          customTextField('query',
                              onchanged: (p0) => readQuery = p0,
                              autovalidateMode: false,
                              enableLabel: false)
                        ],
                      ),
                    ),
                  ),
                  const SizedBox(height: 10),
                  Card(
                    child: Padding(
                      padding: const EdgeInsets.all(10.0),
                      child: Column(
                        crossAxisAlignment: CrossAxisAlignment.start,
                        children: [
                          Row(
                            mainAxisAlignment: MainAxisAlignment.spaceBetween,
                            children: [
                              const Text("Write Data", style: textStyle),
                              IconButton(
                                  onPressed: () => execute("write", context),
                                  icon: const Icon(Icons.play_arrow_rounded))
                            ],
                          ),
                          customTextField('query',
                              onchanged: (p0) => writeQuery = p0,
                              autovalidateMode: false,
                              enableLabel: false)
                        ],
                      ),
                    ),
                  ),
                ],
              ),
            ),
          ),
        ],
      ),
    );
  }

  TextFormField customTextField(String title,
          {void Function(String)? onchanged,
          TextInputType? keyboardType,
          bool autovalidateMode = true,
          bool enableLabel = true}) =>
      TextFormField(
        autocorrect: true,
        autovalidateMode:
            autovalidateMode ? AutovalidateMode.onUserInteraction : null,
        inputFormatters: [
          if (title == "IP address")
            FilteringTextInputFormatter.allow(RegExp(r'[\d\.]')),
          if (title == "Port") ...[
            FilteringTextInputFormatter.digitsOnly,
            LengthLimitingTextInputFormatter(4)
          ]
        ],
        keyboardType: keyboardType,
        onChanged: onchanged,
        decoration: InputDecoration(
            border: title == "Port" || title == "IP address"
                ? const OutlineInputBorder()
                : null,
            hintText: "Enter $title ${title == "Port" ? "number" : ""}",
            labelText: enableLabel ? title : null),
        validator: (value) {
          if (value!.isEmpty) {
            return "Please Enter $title";
          }
          return null;
        },
      );

  connect() async {
    if (ip.isEmpty ||
        port.isEmpty ||
        databaseName.isEmpty ||
        username.isEmpty ||
        password.isEmpty) {
      toastMessage("Please enter all fields", color: Colors.redAccent);

      return;
    }
    _sqlConnection
        .connect(
            ip: ip,
            port: port,
            databaseName: databaseName,
            username: username,
            password: password)
        .then((value) {
      if (value) {
        toastMessage("Connection Established", color: Colors.green);
        pageController.nextPage(
            duration: const Duration(milliseconds: 500),
            curve: Curves.easeInOut);
      } else {
        toastMessage("Connection Failed", color: Colors.redAccent);
      }
    }).onError((e, st) {
      toastMessage(e.toString(), color: Colors.redAccent);
    });
  }

  Future<void> toastMessage(String message,
      {Color color = Colors.blueAccent, String title = ""}) async {
    /// ignore: use_build_context_synchronously
    await ToastMessageBar(
      //Add background color for your toast message
      backgroundColor: color,

      //Add title for your toast message
      title: color == Colors.blueAccent
          ? "INFO"
          : color == Colors.redAccent
              ? "ERROR"
              : color == Colors.green
                  ? "SUCCESS"
                  : title,

      //Add title color for your toast
      titleColor: Colors.white,

      //Add message for your toast
      message: message,

      //Add message color for your toast message
      messageColor: Colors.white,

      //Add duration to display the message
      duration: const Duration(seconds: 3),
    ).show(context);
  }

  execute(String s, BuildContext context) async {
    try {
      if (s == "Read") {
        if (readQuery.isEmpty) {
          toastMessage("Empty query", color: Colors.redAccent);
          return;
        }
        print(readQuery);
        showProgress(context);
        var startTime = DateTime.now();
        var result = await _sqlConnection.getData(readQuery);
        var difference = DateTime.now().difference(startTime);
        if (!mounted) return;
        hideProgress(context);
        print(
            "Duration: $difference and RecordCount:${jsonDecode(result).length}");
        toastMessage(
            "Total Records Count:${jsonDecode(result).length}.\n Duration: $difference");
        // print(result.toString());
      } else {
        if (writeQuery.isEmpty) {
          toastMessage("Empty query", color: Colors.redAccent);
          return;
        }
        showProgress(context);
        var startTime = DateTime.now();
        var result = await _sqlConnection.writeData(writeQuery);
        var difference = DateTime.now().difference(startTime);
        if (!mounted) return;
        hideProgress(context);
        print("Duration: ${DateTime.now().difference(startTime)} ");
        print(result.toString());
        toastMessage(
            "Please check the console for data.\n Duration: $difference");
      }
    } catch (e) {
      hideProgress(context);
      toastMessage(e.toString(), color: Colors.redAccent);
    }
  }

  showProgress(BuildContext context,
          [String alertMessage = "Fetching Data..."]) async =>
      await showDialog(
          context: context,
          builder: (context) =>
              AlertDialog(
                content: Row(
                  mainAxisSize: MainAxisSize.min,
                  children: [
                    const SizedBox.square(
                        dimension: 35, child: CircularProgressIndicator()),
                    const SizedBox(width: 12),
                    Text(
                      alertMessage,
                      style: const TextStyle(fontSize: 20),
                    )
                  ],
                ),
              ));

  hideProgress(BuildContext context) {
    Navigator.pop(context);
  }
}

这个示例展示了如何创建一个简单的Flutter应用程序,通过 mssql_connection 插件连接到SQL Server,执行读取和写入操作,并显示结果。希望这对您有所帮助!如果有任何问题或需要进一步的帮助,请随时提问。


更多关于Flutter数据库连接插件mssql_connection的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html

1 回复

更多关于Flutter数据库连接插件mssql_connection的使用的实战系列教程也可以访问 https://www.itying.com/category-92-b0.html


当然,以下是一个关于如何在Flutter应用中使用mssql_connection插件来连接Microsoft SQL Server数据库的示例代码。请注意,mssql_connection并不是官方或广泛认可的Flutter插件,因此这个示例基于假设存在一个类似的插件(或者你可能需要使用一个类似的库,如sqlserver_dart,并通过平台通道与原生代码交互)。由于直接连接SQL Server在Flutter客户端上并不常见,通常这类操作会在后端服务中处理,但为了说明,这里给出一个假设性的例子。

首先,你需要确保你的pubspec.yaml文件中包含了必要的依赖项(假设插件名为mssql_connection,实际使用时请替换为正确的包名):

dependencies:
  flutter:
    sdk: flutter
  mssql_connection: ^x.y.z  # 替换为实际版本号

然后运行flutter pub get来获取依赖项。

接下来是一个简单的Flutter应用示例,它尝试连接到Microsoft SQL Server并执行一个查询:

import 'package:flutter/material.dart';
import 'dart:async';
import 'package:mssql_connection/mssql_connection.dart'; // 假设的包名

void main() {
  runApp(MyApp());
}

class MyApp extends StatelessWidget {
  @override
  Widget build(BuildContext context) {
    return MaterialApp(
      home: Scaffold(
        appBar: AppBar(
          title: Text('Flutter MSSQL Connection Example'),
        ),
        body: Center(
          child: FutureBuilder<String>(
            future: fetchData(),
            builder: (context, snapshot) {
              if (snapshot.connectionState == ConnectionState.waiting) {
                return CircularProgressIndicator();
              } else if (snapshot.hasError) {
                return Text('Error: ${snapshot.error}');
              } else {
                return Text('Data: ${snapshot.data}');
              }
            },
          ),
        ),
      ),
    );
  }
}

Future<String> fetchData() async {
  String connectionString = 'Server=your_server_address;Database=your_database;User Id=your_username;Password=your_password;';
  
  try {
    // 假设mssql_connection有一个connect方法,并且返回一个连接对象
    var connection = await MSSQLConnection.connect(connectionString);
    
    // 执行查询
    var result = await connection.executeQuery('SELECT TOP 10 * FROM your_table');
    
    // 处理结果(这里假设结果是一个List<Map<String, dynamic>>)
    String dataString = result.map((row) => row.values.join(', ')).join('\n');
    
    // 关闭连接
    await connection.close();
    
    return dataString;
  } catch (e) {
    return 'Failed to fetch data: $e';
  }
}

注意

  1. 上面的代码是基于假设的mssql_connection插件API。实际使用时,你需要查阅该插件的文档来了解正确的API调用方式。
  2. 在Flutter客户端直接连接SQL Server并不推荐,因为这可能会暴露敏感信息(如数据库凭据)并增加安全风险。通常,这种操作应该在后端服务器上进行,Flutter应用通过API与后端服务器通信。
  3. 如果确实需要在Flutter应用中直接处理数据库连接,考虑使用更安全的方法,比如通过安全的API调用、环境变量管理敏感信息等。
  4. 实际上,你可能需要使用原生平台通道与原生代码(如Dart的sqlserver_dart库结合Android/iOS的JDBC/ODBC桥接)来实现与SQL Server的连接。

希望这个示例能帮助你理解如何在Flutter应用中尝试连接SQL Server。如果你遇到具体的问题或需要更详细的指导,请查阅相关插件的文档或寻求社区的帮助。

回到顶部