indexedDB---掌握浏览器内建数据库的基本用法

1.认识indexedDB

        IndexedDB 是一个浏览器内建的数据库,它可以存放对象格式的数据,类似本地存储localstore,但是相比localStore 10MB的存储量,indexedDB可存储的数据量远超过这个数值,具体是多少呢?

默认情况下,浏览器会将自身所在的硬盘位置剩余容量全部作为indexedDB的存储容量,

这里差不多就对应这c盘的剩余容量,所以indexDB有第一个特点,容量大

存储的格式,以对象的键值形式存储数据,注意这里的 id 是一个唯一的索引属性,

在indexedDB中,需要有一个唯一的标识符来区分存储的内容,这里使用的是id,这表示,存储的每一个值内都需要一个唯一的id值,这是第二个特点,统一的唯一标识符(key)

最后它采用的是,对象存储库和存储表的数据存放方式;你可以理解成,indexedDB是一个大的数据对象(object),它内部包含了很多数据库(object),每个数据库内又有很多存储对象表(array),每个表内又有很多键值对(object),

在indexedDB中,有很多上面的这种存储库对象,可以看出这是一个树形结构,根节点就是indexedDB

所以,总结一下,indexedDB:

  1. 容量大
  2. 有唯一标识符(key)
  3. 树形结构的对象存储
  4. 和localStore一样同一个域名下的indexedDB是一致的,否则不一致,每个网页都有各自的indexedDB(补充)

2.indexedDB数据库的使用

查看indexedDB

我们可以在开发者工具中直接查看indexedDB数据库,也可以在控制台打印出来,indexedDB是window对象下的一个属性,

// 浏览器本地数据库
console.log(indexedDB);// window.indexedDB

打开数据库

const request = indexedDB.open(name, version);name —— 字符串,即数据库名称。
version —— 一个正整数版本,默认为 1。返回 openRequest 对象

注意:数据库的相关操作都是异步的,打开、读取和编辑、删除,都需要时间处理,并不是马上执行结束,所以每一个对数据库的相关操作都有回调事件进行监听,

  • success:打开成功,数据库准备就绪 ,request.result 中有了一个数据库对象“Database Object”,这就是一个数据库,我们可以通过它访问这个库的所有数据
  • error:打开失败。
  • upgradeneeded:更新版本,当数据库的版本更新时触发,例如,1->2。

        这里解释一下版本号,一个 数据库在打开时,若没有这个库,则会新建,默认版本号为1;若有,打开时的版本号比原本保存的版本号更高,则会更新这个库,同时触发upgradeneeded事件,一个数据库的版本号只会越来越高,不会出现还原旧版本的情况,这是因为有些特定的操作只能在版本更新时执行(upgradeneeded事件)--- 例如,新建、编辑、删除一个对象存储表

// 浏览器本地数据库
console.log(indexedDB);// window.indexedDB// 打开数据库
const request = indexedDB.open('myDatabase', 1);request.onerror = function(event) {console.error('数据库打开报错');
}request.onupgradeneeded = function(event) {const db = event.target.result;console.log('数据库需要升级');// 创建一个对象存储空间
}request.onsuccess = function(event) {const db = event.target.result;console.log('数据库打开成功');
}

 

新建了一个myDatabase数据库,触发 了一次版本更新,在次执行时版本还是1就不会触发更新升级的事件,

这样就成功新建、打开了一个数据库,

新建一个对象存储表

db.createObjectStore(name[, keyOptions]);name 是存储区名称,例如 "books" 表示书。
keyOptions 是具有以下两个属性之一的可选对象:keyPath —— 对象属性的路径,IndexedDB 将以此路径作为键,例如 id。autoIncrement —— 如果为 true,则自动生成新存储的对象的键,键是一个不断递增的数字。
  •  name:储存表的名称
  • keyOptions: 配置对象,
    • keyPath: 储存数据的标识符
    • autoIncrement:默认为false,若为true,则会自动在储存的对象上添加标识符属性,并附上一个自增的正数值(1,2,3,4......)

要操作对象存储表就需要更新版本号,这个createObjectStore方法只能在更新事件内使用,否则将产生错误

// 打开数据库
const request = indexedDB.open('myDatabase', 2);request.onupgradeneeded = function(event) {const db = event.target.result;console.log('数据库需要升级');// 创建一个对象存储空间db.createObjectStore('imgStore', { keyPath: 'id', autoIncrement: true });console.log('对象存储表创建成功');
}request.onsuccess = function(event) {const db = event.target.result;console.log('数据库打开成功');
}

注意需要增加版本号,否则不触发更新事件,这里新建了一个叫imgStore的对象存储表

添加和读取数据

添加和读取数据都在onsuccess的回调中执行,不需要更新版本,

添加数据add()---参数any

request.onsuccess = function(event) {const db = event.target.result;console.log('数据库打开成功');// 连接数据库的表,比获取读写权限,默认只读const transaction = db.transaction(['imgStore'], 'readwrite');const objectStore = transaction.objectStore('imgStore');// 添加数据const re = objectStore.add({name: 'test',content:'测试数据'});re.onsuccess = function (event) {console.log('文件添加成功');}
}

transaction是一个事务,连接了imgStore,并开放读写权限,之后再通过事务,获取imgStore对象存储表,最后再执行add添加数据,这里添加了一个测试对象,同样添加时一个异步操作,需要回调等待结果,

这里成功添加后可以查看数据表中的内容,如果内容没有出现可以 点击刷新,看到结果后可以发现,多了一个属性id,这个就是存储对象的标识符,前面设置了自动添加,若没有设置自动添加,则需要手动的添加一个id属性,且id的值不能和其他数据相同,否则都会添加失败

读取数据get()---参数标识符的值

request.onsuccess = function(event) {const db = event.target.result;console.log('数据库打开成功');// 连接数据库的表,比获取读写权限,默认只读const transaction = db.transaction(['imgStore'], 'readwrite');const objectStore = transaction.objectStore('imgStore');// // 添加数据// const re = objectStore.add({//   name: 'test',//   content:'测试数据'// });// re.onsuccess = function (event) {//   console.log('文件添加成功');// }// 读取数据const re2 = objectStore.get(1);re2.onsuccess = function (event) {console.log(re2.result);}
}

可以看到成功读取到了id为1的数据,

示例:存储一张图片

了解了添加和读取数据,那我们可以来实现上传一张图片,保存再数据库中,

思路:通过input file 上传一个图片,再将其存为blob,再将blob转成base64存储起来

(有关blob的操作可以参考:js二进制数据,文件---blob对象_js 输出 blob-CSDN博客)

let addFile;request.onsuccess = function (event) {const db = event.target.result;console.log('数据库打开成功');addFile = function (file) {// 连接数据库的表,比获取读写权限,默认只读const transaction = db.transaction(['imgStore'], 'readwrite');const objectStore = transaction.objectStore('imgStore');const re = objectStore.add(file)re.onsuccess = function (event) {console.log('文件添加成功');}}
}const file = document.getElementById('file');
file.addEventListener('change', (event) => {const file = event.target.files[0];if (file.type == 'image/jpeg') { // 如果文件是图片let blob = new Blob([file], { type: 'image/jpeg' });let reader = new FileReader();reader.readAsDataURL(blob);reader.onload = function (event) {let base64 = event.target.result;console.log(base64);addFile({name: file.name,data: base64})}}
})

这样我们就成功存放了一个base64形式的图片文件,

然后我们可以读取出这个图片,渲染再页面上


request.onsuccess = function (event) {const db = event.target.result;console.log('数据库打开成功');let getFile = function(){// 连接数据库的表const transaction = db.transaction(['imgStore'], 'readonly');const objectStore = transaction.objectStore('imgStore');// 获取数据const re = objectStore.get(1);re.onsuccess = function (event) {console.log(re.result);let img = new Image();img.src = re.result.data;img.width=800;document.body.appendChild(img);}}getFile()
}

这样就成功拿到了图片,并且每次刷新后都会保留这个图片,就相当于一个能放大文件的localStore

完整代码展示

index.html

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>本地数据库</title>
</head>
<body><input type="file" name="" id="file"></body>
<script src="index.js"></script>
</html>

index.js 

// 浏览器本地数据库
console.log(indexedDB);// window.indexedDB
let addFile;//添加文件的方法
// 打开数据库
const request = indexedDB.open('myDatabase', 2);request.onerror = function (event) {console.error('数据库打开报错');
}request.onupgradeneeded = function (event) {const db = event.target.result;console.log('数据库需要升级');// 创建一个对象存储空间db.createObjectStore('imgStore', { keyPath: 'id', autoIncrement: true });console.log('对象存储表创建成功');
}request.onsuccess = function (event) {const db = event.target.result;console.log('数据库打开成功');// // 连接数据库的表,获取读写权限,默认只读// const transaction = db.transaction(['imgStore'], 'readwrite');// const objectStore = transaction.objectStore('imgStore');// // 添加数据// const re = objectStore.add({//   name: 'test',//   content:'测试数据'// });// re.onsuccess = function (event) {//   console.log('文件添加成功');// }// 读取数据// const re2 = objectStore.get(1);// re2.onsuccess = function (event) {//   console.log(re2.result);// }addFile = function (file) {// 连接数据库的表,获取读写权限,默认只读const transaction = db.transaction(['imgStore'], 'readwrite');const objectStore = transaction.objectStore('imgStore');const re = objectStore.add(file)re.onsuccess = function (event) {console.log('文件添加成功');}}let getFile = function(){// 连接数据库的表const transaction = db.transaction(['imgStore'], 'readonly');const objectStore = transaction.objectStore('imgStore');// 获取数据const re = objectStore.get(1);re.onsuccess = function (event) {console.log(re.result);let img = new Image();img.src = re.result.data;img.width=800;document.body.appendChild(img);}}getFile()
}const file = document.getElementById('file');
file.addEventListener('change', (event) => {const file = event.target.files[0];if (file.type == 'image/jpeg') { // 如果文件是图片let blob = new Blob([file], { type: 'image/jpeg' });let reader = new FileReader();reader.readAsDataURL(blob);reader.onload = function (event) {let base64 = event.target.result;console.log(base64);addFile({name: file.name,data: base64})}}
})

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.mzph.cn/news/857926.shtml

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

【软件设计】详细设计说明书(word原件,项目直接套用)

软件详细设计说明书 1.系统总体设计 2.性能设计 3.系统功能模块详细设计 4.数据库设计 5.接口设计 6.系统出错处理设计 7.系统处理规定 软件全套资料&#xff1a;本文末个人名片直接获取或者进主页。

C语言笔试题:实现把一个无符号整型数字的二进制序列反序后输出

目录 题目 实例 方法一&#xff1a;直接交换 方法二&#xff1a;间接交换 拓展 题目 编写一个函数&#xff0c;将一个无符号整数的所有位逆序&#xff08;在32位机器下&#xff09; 实例 例如有一个无符号整数 unsigned int num 32; unsigned int 在32位系统中占4个字…

洛谷 P10584 [蓝桥杯 2024 国 A] 数学题(整除分块+杜教筛)

题目 思路来源 登录 - Luogu Spilopelia 题解 参考了两篇洛谷题解&#xff0c;第一篇能得出这个式子&#xff0c;第二篇有比较严格的复杂度分析 结合去年蓝桥杯洛谷P9238&#xff0c;基本就能得出这题的正确做法 代码 #include<bits/stdc.h> #include<iostream&g…

测试辅助工具(抓包工具)的使用2 之 抓包工具的基本用法

1.过滤设置: Filters- --- 勾选use Filters- --- 下拉选择show only the following hosts ---- 输入域名或者ip地址(多个地址用;隔开) --- 点击action(Run filterset now) 2.删除数据 方式一:点击Remove all 方式二: 黑窗口输入cls,回车 删除一条数据:选中数据---右键选择Rem…

C++ | Leetcode C++题解之第179题最大数

题目&#xff1a; 题解&#xff1a; class Solution { public:string largestNumber(vector<int> &nums) {sort(nums.begin(), nums.end(), [](const int &x, const int &y) {return to_string(x) to_string(y) > to_string(y) to_string(x);});if (nu…

基于riscv架构的DAYU800开发板套件介绍

一、简介 润和-SCDAYU800 开发平台基于平头哥高性能 RISC-V 开源架构曳影 TH1520 芯片&#xff0c;集成4核高性能RISC-V处理器玄铁C910的平头哥曳影1520&#xff0c;AI算力达4TOPs支持蓝牙、音频、视频和摄像头等功能,支持多种视频输入输出接口,并提供丰富的扩展接口&#xff…

Apple - Cocoa Event Handling Guide

本文翻译整理自&#xff1a;Cocoa Event Handling Guide&#xff08; https://developer.apple.com/library/archive/documentation/Cocoa/Conceptual/EventOverview/Introduction/Introduction.html#//apple_ref/doc/uid/10000060i 文章目录 一、导言本文件的组织另见 二、事件…

展讯-系统定制修改

1.user版本使用adb 打开文件 build/make/core/main.mk ifeq ($(user_variant),user)ADDITIONAL_DEFAULT_PROPERTIES ro.adb.secure0endif 1.这个ro.adb.secure0&#xff08;0为不显示信任此电脑&#xff0c;1为显示信任此电脑&#xff09; ifeq (true,$(strip $(enable_tar…

centos7系统上安装MySQL8.4图文教程

本章教程&#xff0c;主要记录如何在CentOS7系统上安装MySQL8.4的详细步骤。 一、查看当前系统版本 cat /etc/centos-release二、安装步骤 1、创建mysql目录 cd /usr/local && mkdir mysql && cd mysql2、安装rpm包 yum install https://repo.mysql.com//m…

重复文件清理软件怎么用?分享3个删除重复文件的方法!

删除重复文件能够为电脑腾出很大的存储空间&#xff0c;不信&#xff1f;可以试试看哦&#xff01; 电脑使用久了&#xff0c;都会积累大量的文件&#xff0c;这其中难免会出现重复的文件&#xff0c;这些重复文件没有任何作用&#xff0c;而且会占用着电脑的空间&#xff0c;…

不需要new关键字创建实例?jQuery是如何做到的

这篇文章是jQuery源码专栏的开篇文章了&#xff0c;有人会问为什么都2024年了&#xff0c; 还要研究一个已经过时的框架呢&#xff0c;其实&#xff0c;jQuery对比vue和react这种响应式框架&#xff0c;其在使用上算是过时的&#xff0c;毕竟直接操作DOM远不如操作虚拟DOM来的方…

Python 深入学习局部函数和闭包函数

目录 局部函数与闭包函数的关联 变量捕获与状态保留 应用场景的交集与差异 闭包的本质 局部函数示例 闭包函数示例 局部函数和闭包函数之间存在着密切的联系&#xff0c;同时也有一些本质的区别。 局部函数与闭包函数的关联 局部函数&#xff08;Nested Function&#…

(八)ReactHooks使用规则

ReactHooks使用规则 只能在组件中或者其他自定义Hook函数中使用只能在组件的顶层调用&#xff0c;不能嵌套在if、for、其他函数中

Windows 11 安装hp 1020 plus 打印机驱动 (Ubuntu 20.04.3 LTS 部署cups局域网共享打印服务器)

1 win11 下载HP laserjet 1020 plus驱动,可以官网下载哦 链接下载 2 手动添加hp laserjet 1020驱动: 控制面板-->查看设备和打印机-->打印机和扫描仪-->添加设备-->我需要的打印机不在列表中-->通过手动添加-->按名称选择共享打印机 如果找不到&#xff0…

Android应用保活实践

} override fun onBind(intent: Intent): IBinder? { return mBilder } override fun onStartCommand(intent: Intent, flags: Int, startId: Int): Int { //播放无声音乐 if (mediaPlayer null) { mediaPlayer MediaPlayer.create(this, R.raw.novioce) //声音设置为0 me…

Spring MVC拦截器、文件上传和全局异常处理

目录 1.拦截器1.1.什么是拦截器&#xff1f;1.2 拦截器的API1.3 拦截器的执行顺序1.5 自定义拦截器1.5 登录拦截器案例 2.文件上传2.1 添加依赖2.2 配置文件上传解析器2.3 编写控制器2.4 编写jsp页面2.5 注意事项 3.全局异常处理器3.1 异常处理思路3.2 创建异常处理器3.3 编写异…

FlinkCDC sink paimon 暂不支持exactly-once写入,而通过 幂等写

幂等写入&#xff1a; 一个幂等操作无论执行多少次都会返回同样的结果。例如&#xff0c;重复的向hashmap中插入同样的key-value对就是幂等操作&#xff0c;因为头一次插入操作之后所有的插入操作都不会改变这个hashmap&#xff0c;因为hashmap已经包含这个key-value对了。另一…

vuejs3用gsap实现动画

效果 gsap官网地址&#xff1a; https://gsap.com/ 安装gsap npm i gsap 创建Gsap.vue文件 <script setup> import {reactive, watch} from "vue"; import gsap from "gsap"; const props defineProps({value:{type:Number,default:0} }) cons…

FFmpeg编译4

CPUx86-64 TOOLCHAIN N D K / t o o l c h a i n s / x 8 6 6 4 − 4.9 / p r e b u i l t / l i n u x − x 8 6 6 4 S Y S R O O T NDK/toolchains/x86_64-4.9/prebuilt/linux-x86_64 SYSROOT NDK/toolchains/x866​4−4.9/prebuilt/linux−x866​4SYSROOTNDK/platforms/and…