uniapp封装 SQLite数据库操作接口

针对app端,需要从静态文件里复制数据库原件,然后才能对数据库进行操作,可放在static目录下

如图所示

对应进行复制然后再进行数据库操作,以下所示

javascript 复制代码
/**
 * SQLite数据库操作接口
 * 封装了SQLite的基本操作方法
 */
const DB_NAME = 'robot';
const DB_FILE_NAME = 'robot.db';

// 数据库状态
let dbOpened = false;

/**
 * 复制预置的数据库文件到 _doc 目录
 * 如果 _doc 目录下已存在数据库文件,则跳过复制
 * @returns {Promise<boolean>} 是否成功复制或已存在
 */
function copyPrebuiltDatabase() {
    return new Promise((resolve, reject) => {
        // #ifdef APP-PLUS
        const targetPath = `_doc/${DB_NAME}.db`;
        const sourcePath = `static/db/${DB_FILE_NAME}`;
        
        console.log('检查预置数据库文件...');
        console.log('源文件路径:', sourcePath);
        console.log('目标文件路径:', targetPath);
        
        // 检查目标文件是否已存在
        plus.io.resolveLocalFileSystemURL(targetPath, (entry) => {
            console.log('数据库文件已存在,无需复制');
            resolve(false); // 已存在,不需要复制
        }, (e) => {
            // 文件不存在,需要复制
            console.log('数据库文件不存在,开始复制...');
            
            // 获取源文件
            plus.io.resolveLocalFileSystemURL(sourcePath, (sourceEntry) => {
                // 获取目标目录 (_doc)
                plus.io.resolveLocalFileSystemURL('_doc/', (docEntry) => {
                    // 复制文件
                    sourceEntry.copyTo(docEntry, `${DB_NAME}.db`, (newEntry) => {
                        console.log('数据库文件复制成功:', newEntry.fullPath);
                        resolve(true);
                    }, (copyError) => {
                        console.error('复制数据库文件失败:', copyError);
                        // 复制失败,但不阻止后续操作(可以创建新数据库)
                        resolve(false);
                    });
                }, (docError) => {
                    console.error('获取 _doc 目录失败:', docError);
                    // 如果 _doc 目录不存在,尝试创建
                    plus.io.requestFileSystem(plus.io.PRIVATE_DOC, (fs) => {
                        console.log('文档文件系统已准备就绪');
                        // 重新尝试复制
                        plus.io.resolveLocalFileSystemURL(sourcePath, (sourceEntry2) => {
                            plus.io.resolveLocalFileSystemURL('_doc/', (docEntry2) => {
                                sourceEntry2.copyTo(docEntry2, `${DB_NAME}.db`, (newEntry) => {
                                    console.log('数据库文件复制成功:', newEntry.fullPath);
                                    resolve(true);
                                }, (copyError2) => {
                                    console.error('第二次复制尝试失败:', copyError2);
                                    resolve(false);
                                });
                            });
                        });
                    }, (fsError) => {
                        console.error('请求文件系统失败:', fsError);
                        resolve(false);
                    });
                });
            }, (sourceError) => {
                console.error('找不到预置数据库文件:', sourceError);
                console.log('将创建新的空数据库');
                resolve(false);
            });
        });
        // #endif
        
        // #ifndef APP-PLUS
        console.log('非 App 环境,跳过数据库文件复制');
        resolve(false);
        // #endif
    });
}

// 打开数据库
function openDb() {
    const dbPath = `_doc/${DB_NAME}.db`;
    
    return new Promise((resolve, reject) => {
        plus.sqlite.openDatabase({
            name: DB_NAME,
            path: dbPath,
            success: (e) => {
                console.log('数据库打开成功', e);
                dbOpened = true;
                resolve(e);
            },
            fail: (e) => {
                console.error('数据库打开失败', e);
                dbOpened = false;
                reject(e);
            }
        });
    });
}

// 检查数据库是否已打开
function isOpen() {
    try {
        const opened = plus.sqlite.isOpenDatabase({
            name: DB_NAME,
            path: `_doc/${DB_NAME}.db`,
        });
        dbOpened = opened;
        return opened;
    } catch (e) {
        console.error('检查数据库状态失败:', e);
        return false;
    }
}

// 获取数据库状态
function getDbStatus() {
    return dbOpened;
}

// 检查表是否存在
function isTable(tableName) {
    return new Promise((resolve, reject) => {
        plus.sqlite.selectSql({
            name: DB_NAME, // 使用默认数据库名
            sql: `SELECT name FROM sqlite_master WHERE type='table' AND name='${tableName}'`,
            success: (e) => {
                resolve(e.length > 0);
            },
            fail: (e) => {
                console.error('检查表失败', e);
                resolve(false);
            }
        });
    });
}

// 创建表
function createTab(tableName, fields) {
    return new Promise((resolve, reject) => {
        plus.sqlite.executeSql({
            name: DB_NAME,
            sql: `CREATE TABLE IF NOT EXISTS ${tableName} (${fields})`,
            success: (e) => {
                console.log(`表 ${tableName} 创建成功`);
                resolve(e);
            },
            fail: (e) => {
                console.error(`表 ${tableName} 创建失败`, e);
                reject(e);
            }
        });
    });
}

// 添加数据
function addTabItem(tableName, data) {
    const keys = Object.keys(data);
    const columns = keys.join(',');
    
    // 直接将值拼接到SQL语句中,处理字符串类型的引号
    const values = keys.map(key => {
        const value = data[key];
        if (value === null || value === undefined) {
            return 'NULL';
        } else if (typeof value === 'string') {
            // 转义单引号,避免SQL语法错误
            return `'${value.replace(/'/g, "''")}'`;
        } else if (typeof value === 'number') {
            return value.toString();
        } else {
            return `'${String(value).replace(/'/g, "''")}'`;
        }
    }).join(',');
    
    const sql = `INSERT INTO ${tableName} (${columns}) VALUES (${values})`;
    
    return new Promise((resolve, reject) => {
        console.log('执行SQL:', sql);
        plus.sqlite.executeSql({
            name: DB_NAME,
            sql: sql,
            success: (e) => {
                console.log('数据插入成功', e);
                resolve(e);
            },
            fail: (e) => {
                console.error('数据插入失败', e);
                reject(e);
            }
        });
    });
}

// 更新数据
function updateBySQL(sql) {
    return new Promise((resolve, reject) => {
         console.log('执行SQL:', sql);
        plus.sqlite.executeSql({
            name: DB_NAME,
            sql: sql,
            success: (e) => {
                console.log('数据更新成功', e);
                resolve(e);
            },
            fail: (e) => {
                console.error('数据更新失败', e);
                reject(e);
            }
        });
    });
}

// 查询数据
function selectBySQL(sql) {
    return new Promise((resolve, reject) => {
        console.log('执行查询SQL:', sql);
        plus.sqlite.selectSql({
            name: DB_NAME,
            sql: sql,
            success: (e) => {
                console.log('查询成功', e);
                resolve(e);
            },
            fail: (e) => {
                console.error('查询失败', e);
                reject(e);
            }
        });
    });
}

// 删除数据
function deleteInformationType(tableName, conditions) {
    let whereClause = '';
    const values = [];
    
    if (conditions && typeof conditions === 'object') {
        const conditionKeys = Object.keys(conditions);
        if (conditionKeys.length > 0) {
            const conditionsArray = conditionKeys.map(key => {
                values.push(conditions[key]);
                return `${key} = ?`;
            });
            whereClause = `WHERE ${conditionsArray.join(' AND ')}`;
        }
    }
    
    const sql = `DELETE FROM ${tableName} ${whereClause}`;
    
    return new Promise((resolve, reject) => {
        plus.sqlite.executeSql({
            name: DB_NAME,
            sql: sql,
            args: values,
            success: (e) => {
                console.log('数据删除成功', e);
                resolve(e);
            },
            fail: (e) => {
                console.error('数据删除失败', e);
                reject(e);
            }
        });
    });
}

// 检查字段是否存在
function existsField(tableName, fieldName) {
    return new Promise((resolve, reject) => {
        plus.sqlite.selectSql({
            name: DB_NAME,
            sql: `PRAGMA table_info(${tableName})`,
            success: (e) => {
                const fieldExists = e.some(field => field.name === fieldName);
                resolve([{num: fieldExists ? 1 : 0}]);
            },
            fail: (e) => {
                console.error('检查字段失败', e);
                reject(e);
            }
        });
    });
}

// 检查索引是否存在
function existsIndex(tableName, indexName) {
    return new Promise((resolve, reject) => {
        plus.sqlite.selectSql({
            name: DB_NAME,
            sql: `SELECT name FROM sqlite_master WHERE type='index' AND name='${indexName}' AND tbl_name='${tableName}'`,
            success: (e) => {
                resolve([{num: e.length > 0 ? 1 : 0}]);
            },
            fail: (e) => {
                console.error('检查索引失败', e);
                reject(e);
            }
        });
    });
}

// 创建索引
function createIndex(tableName, indexName, columnName) {
    return new Promise((resolve, reject) => {
        plus.sqlite.executeSql({
            name: DB_NAME,
            sql: `CREATE INDEX IF NOT EXISTS ${indexName} ON ${tableName} (${columnName})`,
            success: (e) => {
                console.log(`索引 ${indexName} 创建成功`);
                resolve(e);
            },
            fail: (e) => {
                console.error(`索引 ${indexName} 创建失败`, e);
                reject(e);
            }
        });
    });
}

export const sqlite = {
    copyPrebuiltDatabase,
    openDb,
    isOpen,
    getDbStatus,
    isTable,
    createTab,
    addTabItem,
    updateBySQL,
    selectBySQL,
    deleteInformationType,
    existsField,
    existsIndex,
    createIndex
};

export default sqlite;

以此为数据库操作接口对三个表进行相应操作,在页面里可直接调用对应方法即可存储数据

javascript 复制代码
import { sqlite } from './index.js';//index.js即为上述的sqlite封装接口

// 施工项目表名
const CONSTRUCTION_PROJECTS_TABLE = 'construction_projects';

// 异常记录表名
const ABNORMAL_RECORDS_TABLE = 'abnormal_records';
// 用户表名
const USER_TABLE = 'user';
// 检测记录表名
const INSPECTION_RECORDS_TABLE = 'inspection_records';

// 数据库初始化标志
let isDatabaseInitialized = false;

// 施工项目表字段定义
const constructionProjectsFields = `
  id INTEGER PRIMARY KEY AUTOINCREMENT,
  project_name TEXT,
  construction_time TEXT,
  construction_address TEXT,
  joint_manufacturer TEXT,
  tape_manufacturer TEXT,
  tape_production_date TEXT,
  voltage INTEGER,
  wire_diameter INTEGER,
  connector_length INTEGER,
  connector_diameter INTEGER,
  status INTEGER DEFAULT 0,
  end_time TEXT,
  created_at TEXT,
  updated_at TEXT,
  user_id INTEGER,
  is_deal INTEGER DEFAULT 0
`;



// 异常记录表字段定义
const abnormalRecordsFields = `
  id INTEGER PRIMARY KEY AUTOINCREMENT,
  abnormal_situation TEXT,
  datetime TEXT
`;

// 用户表字段定义
const userFields = `
  id INTEGER PRIMARY KEY AUTOINCREMENT,
  name TEXT,
  login_time TEXT,
  create_time TEXT,
  telephone TEXT,
  company TEXT
`;

// 检测记录表字段定义
const inspectionRecordsFields = `
  id INTEGER PRIMARY KEY AUTOINCREMENT,
  date TEXT,
  project_id INTEGER,
  result_type TEXT,
  result TEXT,
  description TEXT,
  created_at TEXT,
  user_id INTEGER
`;

// 初始化数据库
async function initDatabase() {

sqlite.openDb();
    // 初始化施工项目表
    try {
        const exists = await sqlite.isTable(CONSTRUCTION_PROJECTS_TABLE);
        if (!exists) {
            await sqlite.createTab(CONSTRUCTION_PROJECTS_TABLE, constructionProjectsFields);
            console.log('施工项目表创建成功');
        } else {
            console.log('施工项目表已存在');
        }
    } catch (error) {
        console.error('初始化施工项目表失败:', error);
    }

    // 初始化异常记录表
    try {
        const exists = await sqlite.isTable(ABNORMAL_RECORDS_TABLE);
        if (!exists) {
            await sqlite.createTab(ABNORMAL_RECORDS_TABLE, abnormalRecordsFields);
            console.log('异常记录表创建成功');
        } else {
            console.log('异常记录表已存在');
        }
    } catch (error) {
        console.error('初始化异常记录表失败:', error);
    }

    // 初始化用户表
    try {
        const exists = await sqlite.isTable(USER_TABLE);
        if (!exists) {
            await sqlite.createTab(USER_TABLE, userFields);
            console.log('用户表创建成功');
        } else {
            console.log('用户表已存在');
        }
    } catch (error) {
        console.error('初始化用户表失败:', error);
    }
    
    // 初始化检测记录表
    try {
        const exists = await sqlite.isTable(INSPECTION_RECORDS_TABLE);
        if (!exists) {
            await sqlite.createTab(INSPECTION_RECORDS_TABLE, inspectionRecordsFields);
            console.log('检测记录表创建成功');
        } else {
            console.log('检测记录表已存在');
        }
    } catch (error) {
        console.error('初始化检测记录表失败:', error);
    }
    
    // 检查并添加缺失的列(无论数据库是否已经初始化过,都会执行此操作)
    await addMissingColumns();
    
    // 标记数据库已初始化
    isDatabaseInitialized = true;
}

// 添加缺失的列
async function addMissingColumns() {
    try {
        // 定义所有需要检查的列及其类型和默认值
        const columns = [
            { name: 'project_name', type: 'TEXT' },
            { name: 'construction_time', type: 'TEXT' },
            { name: 'construction_address', type: 'TEXT' },
            { name: 'joint_manufacturer', type: 'TEXT' },
            { name: 'tape_manufacturer', type: 'TEXT' },
            { name: 'tape_production_date', type: 'TEXT' },
            { name: 'voltage', type: 'INTEGER' },
            { name: 'wire_diameter', type: 'INTEGER' },
            { name: 'connector_length', type: 'INTEGER' },
            { name: 'connector_diameter', type: 'INTEGER' },
            { name: 'status', type: 'INTEGER', defaultValue: 'DEFAULT 0' },
            { name: 'end_time', type: 'TEXT' },
            { name: 'created_at', type: 'TEXT' },
            { name: 'updated_at', type: 'TEXT' },
            { name: 'user_id', type: 'INTEGER' },
            { name: 'is_deal', type: 'INTEGER', defaultValue: 'DEFAULT 0' }
        ];
        
        // 只执行一次 PRAGMA table_info 查询,获取所有列信息
        const existingColumns = await sqlite.selectBySQL(`PRAGMA table_info(${CONSTRUCTION_PROJECTS_TABLE})`);
        const existingColumnNames = existingColumns.map(col => col.name);
        
        // 检查并添加每个缺失的列
        for (const column of columns) {
            if (!existingColumnNames.includes(column.name)) {
                let sql = `ALTER TABLE ${CONSTRUCTION_PROJECTS_TABLE} ADD COLUMN ${column.name} ${column.type}`;
                if (column.defaultValue) {
                    sql += ` ${column.defaultValue}`;
                }
                await sqlite.updateBySQL(sql);
                console.log(`添加 ${column.name} 列成功`);
            }
        }
    } catch (error) {
        console.error('添加缺失列失败:', error);
    }
    
    // 检查并添加检测记录表的缺失列
    try {
        // 检查表是否存在
        const tableExists = await sqlite.isTable(INSPECTION_RECORDS_TABLE);
        if (tableExists) {
            // 定义检测记录表需要的列
            const inspectionColumns = [
                { name: 'project_id', type: 'INTEGER' },
                { name: 'result_type', type: 'TEXT' },
                { name: 'result', type: 'TEXT' },
                { name: 'description', type: 'TEXT' },
                { name: 'user_id', type: 'INTEGER' }
            ];

            // 获取现有列信息
            const existingColumns = await sqlite.selectBySQL(`PRAGMA table_info(${INSPECTION_RECORDS_TABLE})`);
            const existingColumnNames = existingColumns.map(col => col.name);

            // 检查并添加每个缺失的列
            for (const column of inspectionColumns) {
                if (!existingColumnNames.includes(column.name)) {
                    let sql = `ALTER TABLE ${INSPECTION_RECORDS_TABLE} ADD COLUMN ${column.name} ${column.type}`;
                    await sqlite.updateBySQL(sql);
                    console.log(`添加检测记录表 ${column.name} 列成功`);
                }
            }
        }
    } catch (error) {
        console.error('添加检测记录表缺失列失败:', error);
    }
}

// 施工项目相关操作
export const ConstructionProjectsDB = {
    // 初始化数据库
    async init() {
        await initDatabase();
    },

    // 添加施工项目
    async addProject(projectData) {
        const data = {
            project_name: projectData.project_name || '',
            construction_time: projectData.construction_time || '',
            construction_address: projectData.construction_address || '',
            joint_manufacturer: projectData.joint_manufacturer || '',
            tape_manufacturer: projectData.tape_manufacturer || '',
            tape_production_date: projectData.tape_production_date || '',
            voltage: projectData.voltage || null,
            wire_diameter: projectData.wire_diameter || null,
            connector_length: projectData.connector_length || null,
            connector_diameter: projectData.connector_diameter || null,
            status: 0,
            end_time: projectData.end_time || '',
            created_at: projectData.created_at || '',
            updated_at: projectData.updated_at || '',
            user_id: projectData.user_id || null
        };
        
        return await sqlite.addTabItem(CONSTRUCTION_PROJECTS_TABLE, data);
    },

    // 获取所有施工项目
    async getAllProjects() {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE is_deal = 0 ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    },

    // 根据ID获取项目
    async getProjectById(id) {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE id = ${id}`;
        const result = await sqlite.selectBySQL(sql);
        return result.length > 0 ? result[0] : null;
    },
  // 根据userid获取项目
    async getProjectsByUserId(userid) {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE user_id = ${userid} and is_deal = 0`;
        const result = await sqlite.selectBySQL(sql);
        return result;
    },
    // 格式化日期时间
    formatLocalDateTime() {
        const d = new Date();
        const year = d.getFullYear();
        const month = String(d.getMonth() + 1).padStart(2, '0');
        const day = String(d.getDate()).padStart(2, '0');
        const hours = String(d.getHours()).padStart(2, '0');
        const minutes = String(d.getMinutes()).padStart(2, '0');
        const seconds = String(d.getSeconds()).padStart(2, '0');

        return `${year}-${month}-${day} ${hours}:${minutes}:${seconds}`;
    },

    // 更新项目
    async updateProject(id, projectData) {
        const now = this.formatLocalDateTime();
        const updates = Object.entries(projectData).map(([key, value]) => {
            if (value === null || value === undefined) {
                return `"${key}" = NULL`;
            } else if (typeof value === 'string') {
                return `"${key}" = '${value.replace(/'/g, "''")}'`;
            } else {
                return `"${key}" = ${value}`;
            }
        }).join(', ');
        
        const sql = `UPDATE ${CONSTRUCTION_PROJECTS_TABLE} SET ${updates}, updated_at = '${now}' WHERE id = ${id}`;
        return await sqlite.updateBySQL(sql);
    },

    // 删除项目
    async deleteProject(id) {
        const sql =  `UPDATE ${CONSTRUCTION_PROJECTS_TABLE} SET is_deal = 1 WHERE id = ${id}`;
        return await sqlite.updateBySQL(sql);
    },

    // 获取已完结项目
    async getProjectsByStatus() {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE status = 1 ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    },

    // 获取指定用户的已完结项目
    async getCompletedProjectsByUserId(userid) {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE status = 1 AND user_id = ${userid} ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    },

    // 获取未删除的项目
    async getActiveProjects() {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE is_deal = 0 ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    },

    // 根据项目名称获取项目
    async getProjectByName(projectName) {
        const sql = `SELECT * FROM ${CONSTRUCTION_PROJECTS_TABLE} WHERE project_name = '${projectName.replace(/'/g, "''")}'`;
        const result = await sqlite.selectBySQL(sql);
        return result.length > 0 ? result[0] : null;
    },
    
    // 添加检测记录
    async addInspectionRecord(recordData) {
        const data = {
            date: recordData.date || '',
            project_id: recordData.project_id || null,
            result_type: recordData.result_type || '',
            result: recordData.result || '',
            description: recordData.description || '',
            created_at: recordData.created_at || '',
            user_id: recordData.user_id || null,
        };

        return await sqlite.addTabItem(INSPECTION_RECORDS_TABLE, data);
    },
    
    // 获取所有检测记录
    async getAllInspectionRecords() {
        const sql = `SELECT * FROM ${INSPECTION_RECORDS_TABLE} ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    },
    
    // 根据项目ID获取检测记录
    async getInspectionRecordsByProjectId(projectId) {
        const sql = `SELECT * FROM ${INSPECTION_RECORDS_TABLE} WHERE project_id = ${projectId} ORDER BY created_at DESC`;
        return await sqlite.selectBySQL(sql);
    }
};


// 异常记录相关操作
export const AbnormalRecordsDB = {
    // 添加异常记录
    async addRecord(recordData) {
        return await sqlite.addTabItem(ABNORMAL_RECORDS_TABLE, recordData);
    },

    // 获取所有异常记录
    async getAllRecords() {
        const sql = `SELECT * FROM ${ABNORMAL_RECORDS_TABLE} ORDER BY datetime DESC`;
        return await sqlite.selectBySQL(sql);
    },

    // 根据ID获取记录
    async getRecordById(id) {
        const sql = `SELECT * FROM ${ABNORMAL_RECORDS_TABLE} WHERE id = ${id}`;
        const result = await sqlite.selectBySQL(sql);
        return result.length > 0 ? result[0] : null;
    },

    // 删除记录
    async deleteRecord(id) {
        const sql = `DELETE FROM ${ABNORMAL_RECORDS_TABLE} WHERE id = ${id}`;
        return await sqlite.updateBySQL(sql);
    }
};

// 用户相关操作
export const UserDB = {
    // 添加用户
    async addUser(userData) {
        return await sqlite.addTabItem(USER_TABLE, userData);
    },

    // 获取所有用户
    async getAllUsers() {
        const sql = `SELECT * FROM ${USER_TABLE} ORDER BY id ASC`;
        return await sqlite.selectBySQL(sql);
    },

    // 根据ID获取用户
    async getUserById(id) {
        const sql = `SELECT * FROM ${USER_TABLE} WHERE id = ${id}`;
        const result = await sqlite.selectBySQL(sql);
        return result.length > 0 ? result[0] : null;
    },

    // 根据姓名获取用户
    async getUserByName(name) {
        const sql = `SELECT * FROM ${USER_TABLE} WHERE name = '${name}'`;
        const result = await sqlite.selectBySQL(sql);
        return result.length > 0 ? result[0] : null;
    },

    // 更新用户
    async updateUser(id, userData) {
        const updates = Object.entries(userData).map(([key, value]) => 
            `"${key}" = '${value}'`).join(', ');
        
        const sql = `UPDATE ${USER_TABLE} SET ${updates} WHERE id = ${id}`;
        return await sqlite.updateBySQL(sql);
    },

    // 删除用户
    async deleteUser(id) {
        const sql = `DELETE FROM ${USER_TABLE} WHERE id = ${id}`;
        return await sqlite.updateBySQL(sql);
    }
};
相关推荐
代码的奴隶(艾伦·耶格尔)2 小时前
Hbase GUI 可视化软件
大数据·数据库·hbase
快乐非自愿2 小时前
2026年Django生态现代化组件深度解析与实践
数据库·django·sqlite
それども2 小时前
SQL NOT EXISTS理解
数据库·sql
数据知道2 小时前
MongoDB链式复制:配置 Chained Replication 优化跨机房同步
数据库·mongodb
brucelee1862 小时前
芋道 Spring Boot 框架 + AWS S3 图片上传显示
java·开发语言·数据库
222you2 小时前
MongoDB的安装和整合SpringBoot
数据库·spring boot·mongodb
EnglishJun2 小时前
Linux系统编程(十)--- 数据库Sqlite3
数据库·sqlite
秦jh_2 小时前
【Redis】通用命令、string类型
数据库·redis·缓存
不懒不懒2 小时前
【苏宁易购商品评价文本分析实战:从自动化爬取到分词清洗全流程】
运维·数据库·自动化