ph-utils 0.3.5 → 0.4.0

Sign up to get free protection for your applications and to get access to all the features.
package/README.md CHANGED
@@ -1,11 +1,11 @@
1
- ## ph-utils
2
-
3
- 整理了 js 前后端开发(web + nodejs)时常用的一些工具;[详细文档](https://gitee.com/towardly/ph/wikis/Home?sort_id=4035190)
4
-
5
- ### 后端(node server)
6
-
7
- 包含了一些 node 后端开发(web server) 时常用的工具类,包括 `index` 基础工具类(这个类里面的函数同样也适用于前端)、`date` 跟日期相关的工具类、`file` 文件操作相关工具类、`server` 一些只适用于后端的工具(使用了后端的 API 列表)、`validator` 数据验证
8
-
9
- ### 前端(web)
10
-
11
- 包含了一些前端网站开发时常用的工具类,包括 `index` 基础工具类(这个类里面的函数同样也适用于前端)、`date` 跟日期相关的工具类、`dom` 浏览器节点操作相关、`web` 一些只适用于前端相关的工具、`validator` 数据验证
1
+ ## ph-utils
2
+
3
+ 整理了 js 前后端开发(web + nodejs)时常用的一些工具;[详细文档](https://gitee.com/towardly/ph/wikis/Home?sort_id=4035190)
4
+
5
+ ### 后端(node server)
6
+
7
+ 包含了一些 node 后端开发(web server) 时常用的工具类,包括 `index` 基础工具类(这个类里面的函数同样也适用于前端)、`date` 跟日期相关的工具类、`file` 文件操作相关工具类、`server` 一些只适用于后端的工具(使用了后端的 API 列表)、`validator` 数据验证
8
+
9
+ ### 前端(web)
10
+
11
+ 包含了一些前端网站开发时常用的工具类,包括 `index` 基础工具类(这个类里面的函数同样也适用于前端)、`date` 跟日期相关的工具类、`dom` 浏览器节点操作相关、`web` 一些只适用于前端相关的工具、`validator` 数据验证
package/lib/copy.d.ts ADDED
@@ -0,0 +1,11 @@
1
+ /**
2
+ * 复制数据, 可以从多种类型的数据
3
+ * 1. 直接复制文本: await copy("待复制的文本")
4
+ * 2. 复制节点上的 data-copy-text:
5
+ * <button data-copy-text="这是待复制的文本">复制</button>
6
+ * await copy(e.target) // or await copy("#a") or await copy(document.querySelector('#a'))
7
+ * 3. 直接复制节点本身数据: await copy('#a')
8
+ * @param {string | HTMLElement} source 复制源, 从中解析待复制的数据
9
+ * @returns {Promise<boolean>} 是否复制成功
10
+ */
11
+ export declare function copy(source: string | HTMLElement): Promise<boolean>;
package/lib/copy.js ADDED
@@ -0,0 +1,105 @@
1
+ /**
2
+ * 创建一个临时节点缓存待复制数据
3
+ * @param {String} value
4
+ * @return {HTMLElement}
5
+ */
6
+ function createFakeElement(value) {
7
+ const fakeElement = document.createElement('textarea');
8
+ fakeElement.style.border = '0';
9
+ fakeElement.style.padding = '0';
10
+ fakeElement.style.margin = '0';
11
+ fakeElement.style.position = 'absolute';
12
+ fakeElement.style.left = '-9999px';
13
+ fakeElement.style.top = '-9999';
14
+ fakeElement.setAttribute('readonly', '');
15
+ fakeElement.value = value;
16
+ return fakeElement;
17
+ }
18
+ /** 通过执行 execCommand 来执行复制 */
19
+ function copyFromCommand(text) {
20
+ // 添加节点
21
+ const fakeEl = createFakeElement(text);
22
+ document.body.append(fakeEl);
23
+ fakeEl.focus();
24
+ fakeEl.select();
25
+ // 执行复制
26
+ const res = document.execCommand('copy');
27
+ fakeEl.remove(); // 删除节点
28
+ return Promise.resolve(res);
29
+ }
30
+ /** 使用 navigator.clipboard 复制 */
31
+ function copyFromClipboard(text) {
32
+ let theClipboard = navigator.clipboard;
33
+ if (theClipboard != null) {
34
+ return theClipboard
35
+ .writeText(text)
36
+ .then(() => {
37
+ Promise.resolve(true);
38
+ })
39
+ .catch(() => Promise.resolve(false));
40
+ }
41
+ else {
42
+ return Promise.resolve(false);
43
+ }
44
+ }
45
+ /** 解析待复制的文本 */
46
+ function parseCopyText(source) {
47
+ let copyText = null; // 待复制文本
48
+ let sourceEl = null;
49
+ // 获取待复制数据
50
+ if (typeof source === 'string') {
51
+ // 从节点拿数据
52
+ if (source.startsWith('#') || source.startsWith('.')) {
53
+ sourceEl = document.querySelector(source);
54
+ if (sourceEl == null) {
55
+ copyText = source;
56
+ }
57
+ }
58
+ else {
59
+ copyText = source;
60
+ }
61
+ }
62
+ if (source instanceof HTMLElement) {
63
+ sourceEl = source;
64
+ }
65
+ // 从节点获取待复制数据
66
+ if (sourceEl != null) {
67
+ if (sourceEl.hasAttribute('data-copy-text')) {
68
+ copyText = sourceEl.getAttribute('data-copy-text');
69
+ }
70
+ else {
71
+ const tagName = sourceEl.tagName;
72
+ if (tagName === 'INPUT' || tagName === 'TEXTAREA') {
73
+ copyText = sourceEl.value;
74
+ }
75
+ else {
76
+ copyText = sourceEl.textContent;
77
+ }
78
+ }
79
+ }
80
+ return copyText;
81
+ }
82
+ /**
83
+ * 复制数据, 可以从多种类型的数据
84
+ * 1. 直接复制文本: await copy("待复制的文本")
85
+ * 2. 复制节点上的 data-copy-text:
86
+ * <button data-copy-text="这是待复制的文本">复制</button>
87
+ * await copy(e.target) // or await copy("#a") or await copy(document.querySelector('#a'))
88
+ * 3. 直接复制节点本身数据: await copy('#a')
89
+ * @param {string | HTMLElement} source 复制源, 从中解析待复制的数据
90
+ * @returns {Promise<boolean>} 是否复制成功
91
+ */
92
+ export async function copy(source) {
93
+ // 待复制文本
94
+ const copyText = parseCopyText(source);
95
+ if (copyText == null) {
96
+ return Promise.resolve(false);
97
+ }
98
+ const v = await copyFromClipboard(copyText);
99
+ if (v === false) {
100
+ return copyFromCommand(copyText);
101
+ }
102
+ else {
103
+ return Promise.resolve(true);
104
+ }
105
+ }
package/lib/server.js CHANGED
@@ -1,5 +1,5 @@
1
1
  import { exec as execCmd, spawn } from 'child_process';
2
- import { isBlank } from './index';
2
+ import { isBlank } from './index.js';
3
3
  /**
4
4
  * 执行命令
5
5
  * @param cmd 执行的命令
@@ -0,0 +1,45 @@
1
+ /**
2
+ * 缓存相关
3
+ */
4
+ type StorageType = 'session' | 'local';
5
+ interface StorageSetOption {
6
+ storage?: StorageType;
7
+ /** 数据有效期, 单位秒, 默认: -1 - 永久存储 */
8
+ expire?: number;
9
+ }
10
+ /**
11
+ * 存储值到 Storage 中
12
+ * @param key 设置的 key
13
+ * @param value 设置的值
14
+ * @param storage session 或 local
15
+ * @param expire 数据有效期, 单位秒, 默认: -1 - 永久存储
16
+ */
17
+ export declare function set(key: string, value: any, option?: StorageSetOption): void;
18
+ /**
19
+ * 清空所有的缓存内容
20
+ * @param storage 待清空的缓存对象
21
+ */
22
+ export declare function clear(storage?: StorageType): void;
23
+ /**
24
+ * 删除存储到 Storage 中的数据
25
+ * @param key
26
+ * @param storage
27
+ */
28
+ export declare function remove(key: string, storage?: StorageType): void;
29
+ /** 从 Storage 中获取数据时的配置 */
30
+ interface StorageQueryOption {
31
+ /** 数据是否持久化, 默认为: false, 设置为 true 则会在每一次取出数据后删除 */
32
+ delete?: boolean;
33
+ /** 存储对象, session、local */
34
+ storage?: StorageType;
35
+ }
36
+ /**
37
+ * 从 Storage 中取出数据
38
+ * @param key 保存时的 key
39
+ * @param defaultValue 没有数据时的默认值
40
+ * @param delete 是否在取出后,删除数据,默认:false - 取出后删除数据
41
+ * @param storage 使用的 Storage ,可以是 localStorage、sessionStorage
42
+ * @returns Storage 中 key 对应的数据
43
+ */
44
+ export declare function get<T>(key: string, defaultValue?: T, option?: StorageQueryOption): T;
45
+ export {};
package/lib/storage.js ADDED
@@ -0,0 +1,63 @@
1
+ function getStorage(storage = 'session') {
2
+ return storage === 'session' ? sessionStorage : localStorage;
3
+ }
4
+ /**
5
+ * 存储值到 Storage 中
6
+ * @param key 设置的 key
7
+ * @param value 设置的值
8
+ * @param storage session 或 local
9
+ * @param expire 数据有效期, 单位秒, 默认: -1 - 永久存储
10
+ */
11
+ export function set(key, value, option) {
12
+ const opts = { expire: -1, storage: 'session', ...(option || {}) };
13
+ const saveData = JSON.stringify({
14
+ value,
15
+ time: Date.now(),
16
+ expire: opts.expire === -1 ? -1 : Math.floor(Date.now() / 1000) + opts.expire,
17
+ });
18
+ getStorage(opts.storage).setItem(key, saveData);
19
+ }
20
+ /**
21
+ * 清空所有的缓存内容
22
+ * @param storage 待清空的缓存对象
23
+ */
24
+ export function clear(storage) {
25
+ getStorage(storage).clear();
26
+ }
27
+ /**
28
+ * 删除存储到 Storage 中的数据
29
+ * @param key
30
+ * @param storage
31
+ */
32
+ export function remove(key, storage) {
33
+ getStorage(storage).removeItem(key);
34
+ }
35
+ /**
36
+ * 从 Storage 中取出数据
37
+ * @param key 保存时的 key
38
+ * @param defaultValue 没有数据时的默认值
39
+ * @param delete 是否在取出后,删除数据,默认:false - 取出后删除数据
40
+ * @param storage 使用的 Storage ,可以是 localStorage、sessionStorage
41
+ * @returns Storage 中 key 对应的数据
42
+ */
43
+ export function get(key, defaultValue, option) {
44
+ let opts = (option || { delete: false });
45
+ const storage = getStorage(opts.storage);
46
+ let data = storage.getItem(key);
47
+ if (data == null) {
48
+ return defaultValue || null;
49
+ }
50
+ data = JSON.parse(data);
51
+ let d = data.value;
52
+ if (data.expire !== -1) {
53
+ // 数据过期
54
+ if (Math.floor(Date.now() / 1000) > data.expire) {
55
+ d = null;
56
+ storage.removeItem(key);
57
+ }
58
+ }
59
+ if (opts.delete) {
60
+ storage.removeItem(key);
61
+ }
62
+ return d || defaultValue;
63
+ }
package/lib/web.js CHANGED
@@ -1,7 +1,7 @@
1
1
  /**
2
2
  * web(浏览器) 端工具类
3
3
  */
4
- import { isBlank } from './index';
4
+ import { isBlank } from './index.js';
5
5
  /**
6
6
  * 解析 Form 表单中的 input 元素的数据为 JSON 格式,key: input-name;value: input-value
7
7
  * @param form {object} Form 节点对象
package/package.json CHANGED
@@ -38,9 +38,17 @@
38
38
  "types": "./lib/dom.d.ts",
39
39
  "import": "./lib/dom.js"
40
40
  },
41
+ "./copy": {
42
+ "types": "./lib/copy.d.ts",
43
+ "import": "./lib/copy.js"
44
+ },
45
+ "./storage": {
46
+ "types": "./lib/storage.d.ts",
47
+ "import": "./lib/storage.js"
48
+ },
41
49
  "./*": "./lib/*"
42
50
  },
43
- "version": "0.3.5",
51
+ "version": "0.4.0",
44
52
  "type": "module",
45
53
  "repository": {
46
54
  "type": "git",
@@ -54,8 +62,8 @@
54
62
  },
55
63
  "homepage": "https://gitee.com/towardly/ph/tree/master/packages/utils",
56
64
  "devDependencies": {
57
- "@types/node": "^20.3.1",
58
- "typescript": "^5.1.3"
65
+ "@types/node": "^20.9.0",
66
+ "typescript": "^5.2.2"
59
67
  },
60
68
  "files": [
61
69
  "lib"
File without changes
File without changes