mirror of
https://github.com/Koenkk/zigbee-OTA.git
synced 2026-06-24 13:36:14 +00:00
fix(ignore): Migrate to Biome 2 (#791)
This commit is contained in:
42
biome.json
42
biome.json
@@ -1,6 +1,10 @@
|
|||||||
{
|
{
|
||||||
"$schema": "https://biomejs.dev/schemas/1.9.4/schema.json",
|
"$schema": "https://biomejs.dev/schemas/2.0.5/schema.json",
|
||||||
"vcs": { "enabled": true, "clientKind": "git", "useIgnoreFile": true },
|
"vcs": {
|
||||||
|
"enabled": true,
|
||||||
|
"clientKind": "git",
|
||||||
|
"useIgnoreFile": true
|
||||||
|
},
|
||||||
"formatter": {
|
"formatter": {
|
||||||
"indentStyle": "space",
|
"indentStyle": "space",
|
||||||
"indentWidth": 4,
|
"indentWidth": 4,
|
||||||
@@ -8,17 +12,18 @@
|
|||||||
"bracketSpacing": false
|
"bracketSpacing": false
|
||||||
},
|
},
|
||||||
"files": {
|
"files": {
|
||||||
"ignore": [
|
"includes": [
|
||||||
"package.json",
|
"**",
|
||||||
"./index-stackinfo.json",
|
"!package.json",
|
||||||
"./index.json",
|
"!index-stackinfo.json",
|
||||||
"./index1.json",
|
"!index.json",
|
||||||
"./.cache",
|
"!index1.json",
|
||||||
"./cacerts",
|
"!.cache",
|
||||||
"./images",
|
"!cacerts",
|
||||||
"./images1",
|
"!images",
|
||||||
"./not-in-manifest-images",
|
"!images1",
|
||||||
"./not-in-manifest-images1"
|
"!not-in-manifest-images",
|
||||||
|
"!not-in-manifest-images1"
|
||||||
]
|
]
|
||||||
},
|
},
|
||||||
"linter": {
|
"linter": {
|
||||||
@@ -55,7 +60,16 @@
|
|||||||
}
|
}
|
||||||
]
|
]
|
||||||
}
|
}
|
||||||
}
|
},
|
||||||
|
"useAsConstAssertion": "error",
|
||||||
|
"useDefaultParameterLast": "error",
|
||||||
|
"useEnumInitializers": "error",
|
||||||
|
"useSelfClosingElements": "error",
|
||||||
|
"useSingleVarDeclarator": "error",
|
||||||
|
"noUnusedTemplateLiteral": "error",
|
||||||
|
"useNumberNamespace": "error",
|
||||||
|
"noInferrableTypes": "error",
|
||||||
|
"noUselessElse": "error"
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -48,7 +48,7 @@
|
|||||||
"devDependencies": {
|
"devDependencies": {
|
||||||
"@actions/core": "^1.11.1",
|
"@actions/core": "^1.11.1",
|
||||||
"@actions/github": "^6.0.1",
|
"@actions/github": "^6.0.1",
|
||||||
"@biomejs/biome": "^1.9.4",
|
"@biomejs/biome": "^2.0.5",
|
||||||
"@octokit/rest": "^22.0.0",
|
"@octokit/rest": "^22.0.0",
|
||||||
"@types/node": "^24.0.3",
|
"@types/node": "^24.0.3",
|
||||||
"@vitest/coverage-v8": "^3.2.4",
|
"@vitest/coverage-v8": "^3.2.4",
|
||||||
|
|||||||
74
pnpm-lock.yaml
generated
74
pnpm-lock.yaml
generated
@@ -19,8 +19,8 @@ importers:
|
|||||||
specifier: ^6.0.1
|
specifier: ^6.0.1
|
||||||
version: 6.0.1
|
version: 6.0.1
|
||||||
'@biomejs/biome':
|
'@biomejs/biome':
|
||||||
specifier: ^1.9.4
|
specifier: ^2.0.5
|
||||||
version: 1.9.4
|
version: 2.0.5
|
||||||
'@octokit/rest':
|
'@octokit/rest':
|
||||||
specifier: ^22.0.0
|
specifier: ^22.0.0
|
||||||
version: 22.0.0
|
version: 22.0.0
|
||||||
@@ -79,55 +79,55 @@ packages:
|
|||||||
resolution: {integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==}
|
resolution: {integrity: sha512-6zABk/ECA/QYSCQ1NGiVwwbQerUCZ+TQbp64Q3AgmfNvurHH0j8TtXa1qbShXA6qqkpAj4V5W8pP6mLe1mcMqA==}
|
||||||
engines: {node: '>=18'}
|
engines: {node: '>=18'}
|
||||||
|
|
||||||
'@biomejs/biome@1.9.4':
|
'@biomejs/biome@2.0.5':
|
||||||
resolution: {integrity: sha512-1rkd7G70+o9KkTn5KLmDYXihGoTaIGO9PIIN2ZB7UJxFrWw04CZHPYiMRjYsaDvVV7hP1dYNRLxSANLaBFGpog==}
|
resolution: {integrity: sha512-MztFGhE6cVjf3QmomWu83GpTFyWY8KIcskgRf2AqVEMSH4qI4rNdBLdpAQ11TNK9pUfLGz3IIOC1ZYwgBePtig==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
hasBin: true
|
hasBin: true
|
||||||
|
|
||||||
'@biomejs/cli-darwin-arm64@1.9.4':
|
'@biomejs/cli-darwin-arm64@2.0.5':
|
||||||
resolution: {integrity: sha512-bFBsPWrNvkdKrNCYeAp+xo2HecOGPAy9WyNyB/jKnnedgzl4W4Hb9ZMzYNbf8dMCGmUdSavlYHiR01QaYR58cw==}
|
resolution: {integrity: sha512-VIIWQv9Rcj9XresjCf3isBFfWjFStsdGZvm8SmwJzKs/22YQj167ge7DkxuaaZbNf2kmYif0AcjAKvtNedEoEw==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [darwin]
|
os: [darwin]
|
||||||
|
|
||||||
'@biomejs/cli-darwin-x64@1.9.4':
|
'@biomejs/cli-darwin-x64@2.0.5':
|
||||||
resolution: {integrity: sha512-ngYBh/+bEedqkSevPVhLP4QfVPCpb+4BBe2p7Xs32dBgs7rh9nY2AIYUL6BgLw1JVXV8GlpKmb/hNiuIxfPfZg==}
|
resolution: {integrity: sha512-DRpGxBgf5Z7HUFcNUB6n66UiD4VlBlMpngNf32wPraxX8vYU6N9cb3xQWOXIQVBBQ64QfsSLJnjNu79i/LNmSg==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [darwin]
|
os: [darwin]
|
||||||
|
|
||||||
'@biomejs/cli-linux-arm64-musl@1.9.4':
|
'@biomejs/cli-linux-arm64-musl@2.0.5':
|
||||||
resolution: {integrity: sha512-v665Ct9WCRjGa8+kTr0CzApU0+XXtRgwmzIf1SeKSGAv+2scAlW6JR5PMFo6FzqqZ64Po79cKODKf3/AAmECqA==}
|
resolution: {integrity: sha512-OpflTCOw/ElEs7QZqN/HFaSViPHjAsAPxFJ22LhWUWvuJgcy/Z8+hRV0/3mk/ZRWy5A6fCDKHZqAxU+xB6W4mA==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
|
|
||||||
'@biomejs/cli-linux-arm64@1.9.4':
|
'@biomejs/cli-linux-arm64@2.0.5':
|
||||||
resolution: {integrity: sha512-fJIW0+LYujdjUgJJuwesP4EjIBl/N/TcOX3IvIHJQNsAqvV2CHIogsmA94BPG6jZATS4Hi+xv4SkBBQSt1N4/g==}
|
resolution: {integrity: sha512-FQTfDNMXOknf8+g9Eede2daaduRjTC2SNbfWPNFMadN9K3UKjeZ62jwiYxztPaz9zQQsZU8VbddQIaeQY5CmIA==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
|
|
||||||
'@biomejs/cli-linux-x64-musl@1.9.4':
|
'@biomejs/cli-linux-x64-musl@2.0.5':
|
||||||
resolution: {integrity: sha512-gEhi/jSBhZ2m6wjV530Yy8+fNqG8PAinM3oV7CyO+6c3CEh16Eizm21uHVsyVBEB6RIM8JHIl6AGYCv6Q6Q9Tg==}
|
resolution: {integrity: sha512-9lmjCnajAzpZXbav2P6D87ugkhnaDpJtDvOH5uQbY2RXeW6Rq18uOUltxgacGBP+d8GusTr+s3IFOu7SN0Ok8g==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
|
|
||||||
'@biomejs/cli-linux-x64@1.9.4':
|
'@biomejs/cli-linux-x64@2.0.5':
|
||||||
resolution: {integrity: sha512-lRCJv/Vi3Vlwmbd6K+oQ0KhLHMAysN8lXoCI7XeHlxaajk06u7G+UsFSO01NAs5iYuWKmVZjmiOzJ0OJmGsMwg==}
|
resolution: {integrity: sha512-znpfydUDPuDkyBTulnODrQVK2FaG/4hIOPcQSsF2GeauQOYrBAOplj0etGB0NUrr0dFsvaQ15nzDXYb60ACoiw==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [linux]
|
os: [linux]
|
||||||
|
|
||||||
'@biomejs/cli-win32-arm64@1.9.4':
|
'@biomejs/cli-win32-arm64@2.0.5':
|
||||||
resolution: {integrity: sha512-tlbhLk+WXZmgwoIKwHIHEBZUwxml7bRJgk0X2sPyNR3S93cdRq6XulAZRQJ17FYGGzWne0fgrXBKpl7l4M87Hg==}
|
resolution: {integrity: sha512-CP2wKQB+gh8HdJTFKYRFETqReAjxlcN9AlYDEoye8v2eQp+L9v+PUeDql/wsbaUhSsLR0sjj3PtbBtt+02AN3A==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [arm64]
|
cpu: [arm64]
|
||||||
os: [win32]
|
os: [win32]
|
||||||
|
|
||||||
'@biomejs/cli-win32-x64@1.9.4':
|
'@biomejs/cli-win32-x64@2.0.5':
|
||||||
resolution: {integrity: sha512-8Y5wMhVIPaWe6jw2H+KlEm4wP/f7EW3810ZLmDlrEEy5KvBsb9ECEfu/kMWD484ijfQ8+nIi0giMgu9g1UAuuA==}
|
resolution: {integrity: sha512-Sw3rz2m6bBADeQpr3+MD7Ch4E1l15DTt/+dfqKnwkm3cn4BrYwnArmvKeZdVsFRDjMyjlKIP88bw1r7o+9aqzw==}
|
||||||
engines: {node: '>=14.21.3'}
|
engines: {node: '>=14.21.3'}
|
||||||
cpu: [x64]
|
cpu: [x64]
|
||||||
os: [win32]
|
os: [win32]
|
||||||
@@ -1061,39 +1061,39 @@ snapshots:
|
|||||||
|
|
||||||
'@bcoe/v8-coverage@1.0.2': {}
|
'@bcoe/v8-coverage@1.0.2': {}
|
||||||
|
|
||||||
'@biomejs/biome@1.9.4':
|
'@biomejs/biome@2.0.5':
|
||||||
optionalDependencies:
|
optionalDependencies:
|
||||||
'@biomejs/cli-darwin-arm64': 1.9.4
|
'@biomejs/cli-darwin-arm64': 2.0.5
|
||||||
'@biomejs/cli-darwin-x64': 1.9.4
|
'@biomejs/cli-darwin-x64': 2.0.5
|
||||||
'@biomejs/cli-linux-arm64': 1.9.4
|
'@biomejs/cli-linux-arm64': 2.0.5
|
||||||
'@biomejs/cli-linux-arm64-musl': 1.9.4
|
'@biomejs/cli-linux-arm64-musl': 2.0.5
|
||||||
'@biomejs/cli-linux-x64': 1.9.4
|
'@biomejs/cli-linux-x64': 2.0.5
|
||||||
'@biomejs/cli-linux-x64-musl': 1.9.4
|
'@biomejs/cli-linux-x64-musl': 2.0.5
|
||||||
'@biomejs/cli-win32-arm64': 1.9.4
|
'@biomejs/cli-win32-arm64': 2.0.5
|
||||||
'@biomejs/cli-win32-x64': 1.9.4
|
'@biomejs/cli-win32-x64': 2.0.5
|
||||||
|
|
||||||
'@biomejs/cli-darwin-arm64@1.9.4':
|
'@biomejs/cli-darwin-arm64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-darwin-x64@1.9.4':
|
'@biomejs/cli-darwin-x64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-linux-arm64-musl@1.9.4':
|
'@biomejs/cli-linux-arm64-musl@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-linux-arm64@1.9.4':
|
'@biomejs/cli-linux-arm64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-linux-x64-musl@1.9.4':
|
'@biomejs/cli-linux-x64-musl@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-linux-x64@1.9.4':
|
'@biomejs/cli-linux-x64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-win32-arm64@1.9.4':
|
'@biomejs/cli-win32-arm64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@biomejs/cli-win32-x64@1.9.4':
|
'@biomejs/cli-win32-x64@2.0.5':
|
||||||
optional: true
|
optional: true
|
||||||
|
|
||||||
'@esbuild/aix-ppc64@0.25.5':
|
'@esbuild/aix-ppc64@0.25.5':
|
||||||
|
|||||||
@@ -1,7 +1,6 @@
|
|||||||
import type {ExtraMetas} from "../types.js";
|
|
||||||
|
|
||||||
import {getJson, getLatestImage, readCacheJson, writeCacheJson} from "../common.js";
|
import {getJson, getLatestImage, readCacheJson, writeCacheJson} from "../common.js";
|
||||||
import {processFirmwareImage} from "../process_firmware_image.js";
|
import {processFirmwareImage} from "../process_firmware_image.js";
|
||||||
|
import type {ExtraMetas} from "../types.js";
|
||||||
|
|
||||||
type ReleaseAssetJson = {
|
type ReleaseAssetJson = {
|
||||||
url: string;
|
url: string;
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
import type {ExtraMetas, ExtraMetasWithFileName, ImageHeader, RepoImageMeta} from "./types";
|
|
||||||
|
|
||||||
import assert from "node:assert";
|
import assert from "node:assert";
|
||||||
import {exec} from "node:child_process";
|
import {exec} from "node:child_process";
|
||||||
import {createHash} from "node:crypto";
|
import {createHash} from "node:crypto";
|
||||||
import {existsSync, mkdirSync, readFileSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
import {existsSync, mkdirSync, readFileSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
|
import type {ExtraMetas, ExtraMetasWithFileName, ImageHeader, RepoImageMeta} from "./types";
|
||||||
|
|
||||||
export const UPGRADE_FILE_IDENTIFIER = Buffer.from([0x1e, 0xf1, 0xee, 0x0b]);
|
export const UPGRADE_FILE_IDENTIFIER = Buffer.from([0x1e, 0xf1, 0xee, 0x0b]);
|
||||||
export const BASE_REPO_URL = "https://raw.githubusercontent.com/Koenkk/zigbee-OTA/";
|
export const BASE_REPO_URL = "https://raw.githubusercontent.com/Koenkk/zigbee-OTA/";
|
||||||
|
|||||||
@@ -1,18 +1,17 @@
|
|||||||
|
import assert from "node:assert";
|
||||||
|
import {existsSync, mkdirSync, writeFileSync} from "node:fs";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import assert from "node:assert";
|
|
||||||
import {existsSync, mkdirSync, writeFileSync} from "node:fs";
|
|
||||||
|
|
||||||
import {
|
import {
|
||||||
BASE_INDEX_MANIFEST_FILENAME,
|
BASE_INDEX_MANIFEST_FILENAME,
|
||||||
PREV_INDEX_MANIFEST_FILENAME,
|
execute,
|
||||||
PR_ARTIFACT_DIFF_FILEPATH,
|
PR_ARTIFACT_DIFF_FILEPATH,
|
||||||
PR_ARTIFACT_DIR,
|
PR_ARTIFACT_DIR,
|
||||||
PR_ARTIFACT_ERROR_FILEPATH,
|
PR_ARTIFACT_ERROR_FILEPATH,
|
||||||
PR_ARTIFACT_NUMBER_FILEPATH,
|
PR_ARTIFACT_NUMBER_FILEPATH,
|
||||||
execute,
|
PREV_INDEX_MANIFEST_FILENAME,
|
||||||
readManifest,
|
readManifest,
|
||||||
writeManifest,
|
writeManifest,
|
||||||
} from "./common.js";
|
} from "./common.js";
|
||||||
|
|||||||
@@ -1,10 +1,9 @@
|
|||||||
|
import {readdirSync, readFileSync, writeFileSync} from "node:fs";
|
||||||
|
import path from "node:path";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import {readFileSync, readdirSync, writeFileSync} from "node:fs";
|
|
||||||
import path from "node:path";
|
|
||||||
|
|
||||||
export const CACERTS_DIR = "cacerts";
|
export const CACERTS_DIR = "cacerts";
|
||||||
export const CACERTS_CONCAT_FILEPATH = "cacerts.pem";
|
export const CACERTS_CONCAT_FILEPATH = "cacerts.pem";
|
||||||
|
|
||||||
|
|||||||
@@ -1,11 +1,9 @@
|
|||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
import {BASE_IMAGES_DIR, BASE_INDEX_MANIFEST_FILENAME, execute, PREV_IMAGES_DIR, PREV_INDEX_MANIFEST_FILENAME, readManifest} from "./common.js";
|
||||||
import type {RepoImageMeta} from "./types.js";
|
import type {RepoImageMeta} from "./types.js";
|
||||||
|
|
||||||
import {BASE_IMAGES_DIR, BASE_INDEX_MANIFEST_FILENAME, PREV_IMAGES_DIR, PREV_INDEX_MANIFEST_FILENAME, execute, readManifest} from "./common.js";
|
|
||||||
|
|
||||||
// about 3 lines
|
// about 3 lines
|
||||||
const MAX_RELEASE_NOTES_LENGTH = 380;
|
const MAX_RELEASE_NOTES_LENGTH = 380;
|
||||||
|
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
|
import assert from "node:assert";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import assert from "node:assert";
|
|
||||||
|
|
||||||
const IGNORE_OTA_WORKFLOW_LABEL = "ignore-ota-workflow";
|
const IGNORE_OTA_WORKFLOW_LABEL = "ignore-ota-workflow";
|
||||||
|
|
||||||
export async function createPRToDefault(
|
export async function createPRToDefault(
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
|
import assert from "node:assert";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import assert from "node:assert";
|
|
||||||
|
|
||||||
import {BASE_IMAGES_DIR} from "./common.js";
|
import {BASE_IMAGES_DIR} from "./common.js";
|
||||||
|
|
||||||
export async function getChangedOtaFiles(
|
export async function getChangedOtaFiles(
|
||||||
|
|||||||
@@ -1,11 +1,10 @@
|
|||||||
|
import {readFileSync, writeFileSync} from "node:fs";
|
||||||
|
import {join} from "node:path";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import {readFileSync, writeFileSync} from "node:fs";
|
import {BASE_INDEX_MANIFEST_FILENAME, BASE_REPO_URL, parseImageHeader, REPO_BRANCH, readManifest, UPGRADE_FILE_IDENTIFIER} from "./common.js";
|
||||||
import {join} from "node:path";
|
|
||||||
|
|
||||||
import {BASE_INDEX_MANIFEST_FILENAME, BASE_REPO_URL, REPO_BRANCH, UPGRADE_FILE_IDENTIFIER, parseImageHeader, readManifest} from "./common.js";
|
|
||||||
|
|
||||||
enum ZigBeeStackVersion {
|
enum ZigBeeStackVersion {
|
||||||
ZigBee2006 = 0x0000,
|
ZigBee2006 = 0x0000,
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
|
import {existsSync, mkdirSync} from "node:fs";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import {existsSync, mkdirSync} from "node:fs";
|
|
||||||
|
|
||||||
import {ALL_AUTODL_MANUFACTURERS, CACHE_DIR} from "./common.js";
|
import {ALL_AUTODL_MANUFACTURERS, CACHE_DIR} from "./common.js";
|
||||||
|
|
||||||
export async function overwriteCache(github: Octokit, core: typeof CoreApi, context: Context, manufacturersCSV?: string): Promise<void> {
|
export async function overwriteCache(github: Octokit, core: typeof CoreApi, context: Context, manufacturersCSV?: string): Promise<void> {
|
||||||
|
|||||||
@@ -1,26 +1,23 @@
|
|||||||
import type CoreApi from "@actions/core";
|
|
||||||
import type {Context} from "@actions/github/lib/context";
|
|
||||||
import type {Octokit} from "@octokit/rest";
|
|
||||||
|
|
||||||
import type {ExtraMetas, GHExtraMetas, RepoImageMeta} from "./types.js";
|
|
||||||
|
|
||||||
import assert from "node:assert";
|
import assert from "node:assert";
|
||||||
import {readFileSync, renameSync} from "node:fs";
|
import {readFileSync, renameSync} from "node:fs";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
|
import type CoreApi from "@actions/core";
|
||||||
|
import type {Context} from "@actions/github/lib/context";
|
||||||
|
import type {Octokit} from "@octokit/rest";
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_DIR,
|
|
||||||
PREV_IMAGES_DIR,
|
|
||||||
ParsedImageStatus,
|
|
||||||
UPGRADE_FILE_IDENTIFIER,
|
|
||||||
addImageToBase,
|
addImageToBase,
|
||||||
addImageToPrev,
|
addImageToPrev,
|
||||||
|
BASE_IMAGES_DIR,
|
||||||
findMatchImage,
|
findMatchImage,
|
||||||
getOutDir,
|
getOutDir,
|
||||||
getParsedImageStatus,
|
getParsedImageStatus,
|
||||||
getValidMetas,
|
getValidMetas,
|
||||||
|
ParsedImageStatus,
|
||||||
|
PREV_IMAGES_DIR,
|
||||||
parseImageHeader,
|
parseImageHeader,
|
||||||
|
UPGRADE_FILE_IDENTIFIER,
|
||||||
} from "./common.js";
|
} from "./common.js";
|
||||||
|
import type {ExtraMetas, GHExtraMetas, RepoImageMeta} from "./types.js";
|
||||||
|
|
||||||
const EXTRA_METAS_PR_BODY_START_TAG = "```json";
|
const EXTRA_METAS_PR_BODY_START_TAG = "```json";
|
||||||
const EXTRA_METAS_PR_BODY_END_TAG = "```";
|
const EXTRA_METAS_PR_BODY_END_TAG = "```";
|
||||||
|
|||||||
@@ -1,11 +1,10 @@
|
|||||||
|
import assert from "node:assert";
|
||||||
|
import {existsSync, readFileSync, writeFileSync} from "node:fs";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import assert from "node:assert";
|
import {execute, PR_ARTIFACT_DIR, PR_DIFF_FILENAME, PR_ERROR_FILENAME, PR_NUMBER_FILENAME} from "./common.js";
|
||||||
import {existsSync, readFileSync, writeFileSync} from "node:fs";
|
|
||||||
|
|
||||||
import {PR_ARTIFACT_DIR, PR_DIFF_FILENAME, PR_ERROR_FILENAME, PR_NUMBER_FILENAME, execute} from "./common.js";
|
|
||||||
|
|
||||||
export async function reportOtaPR(github: Octokit, core: typeof CoreApi, context: Context): Promise<void> {
|
export async function reportOtaPR(github: Octokit, core: typeof CoreApi, context: Context): Promise<void> {
|
||||||
assert(context.payload.workflow_run, "Not a workflow run");
|
assert(context.payload.workflow_run, "Not a workflow run");
|
||||||
|
|||||||
@@ -1,33 +1,30 @@
|
|||||||
|
import {existsSync, lstatSync, mkdirSync, readdirSync, readFileSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
||||||
|
import path from "node:path";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import type {RepoImageMeta} from "./types";
|
|
||||||
|
|
||||||
import {existsSync, lstatSync, mkdirSync, readFileSync, readdirSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
|
||||||
import path from "node:path";
|
|
||||||
|
|
||||||
import {
|
import {
|
||||||
|
addImageToBase,
|
||||||
|
addImageToPrev,
|
||||||
BASE_IMAGES_DIR,
|
BASE_IMAGES_DIR,
|
||||||
BASE_INDEX_MANIFEST_FILENAME,
|
BASE_INDEX_MANIFEST_FILENAME,
|
||||||
BASE_REPO_URL,
|
BASE_REPO_URL,
|
||||||
PREV_IMAGES_DIR,
|
|
||||||
PREV_INDEX_MANIFEST_FILENAME,
|
|
||||||
ParsedImageStatus,
|
|
||||||
REPO_BRANCH,
|
|
||||||
UPGRADE_FILE_IDENTIFIER,
|
|
||||||
addImageToBase,
|
|
||||||
addImageToPrev,
|
|
||||||
computeSHA512,
|
computeSHA512,
|
||||||
findMatchImage,
|
findMatchImage,
|
||||||
getOutDir,
|
getOutDir,
|
||||||
getParsedImageStatus,
|
getParsedImageStatus,
|
||||||
getRepoFirmwareFileUrl,
|
getRepoFirmwareFileUrl,
|
||||||
getValidMetas,
|
getValidMetas,
|
||||||
|
ParsedImageStatus,
|
||||||
|
PREV_IMAGES_DIR,
|
||||||
|
PREV_INDEX_MANIFEST_FILENAME,
|
||||||
parseImageHeader,
|
parseImageHeader,
|
||||||
|
REPO_BRANCH,
|
||||||
readManifest,
|
readManifest,
|
||||||
|
UPGRADE_FILE_IDENTIFIER,
|
||||||
writeManifest,
|
writeManifest,
|
||||||
} from "./common.js";
|
} from "./common.js";
|
||||||
|
import type {RepoImageMeta} from "./types";
|
||||||
|
|
||||||
/** These are now handled by autodl */
|
/** These are now handled by autodl */
|
||||||
const IGNORE_3RD_PARTIES = ["https://github.com/fairecasoimeme/", "https://github.com/xyzroe/"];
|
const IGNORE_3RD_PARTIES = ["https://github.com/fairecasoimeme/", "https://github.com/xyzroe/"];
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
|
import {existsSync, mkdirSync, rmSync} from "node:fs";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import {existsSync, mkdirSync, rmSync} from "node:fs";
|
|
||||||
|
|
||||||
import {ALL_AUTODL_MANUFACTURERS, BASE_INDEX_MANIFEST_FILENAME, CACHE_DIR, PREV_INDEX_MANIFEST_FILENAME, TMP_DIR, writeManifest} from "./common.js";
|
import {ALL_AUTODL_MANUFACTURERS, BASE_INDEX_MANIFEST_FILENAME, CACHE_DIR, PREV_INDEX_MANIFEST_FILENAME, TMP_DIR, writeManifest} from "./common.js";
|
||||||
|
|
||||||
export async function runAutodl(github: Octokit, core: typeof CoreApi, context: Context, manufacturersCSV?: string): Promise<void> {
|
export async function runAutodl(github: Octokit, core: typeof CoreApi, context: Context, manufacturersCSV?: string): Promise<void> {
|
||||||
|
|||||||
@@ -1,9 +1,8 @@
|
|||||||
|
import assert from "node:assert";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
|
||||||
import assert from "node:assert";
|
|
||||||
|
|
||||||
import {BASE_INDEX_MANIFEST_FILENAME, PREV_INDEX_MANIFEST_FILENAME, readManifest, writeManifest} from "./common.js";
|
import {BASE_INDEX_MANIFEST_FILENAME, PREV_INDEX_MANIFEST_FILENAME, readManifest, writeManifest} from "./common.js";
|
||||||
import {getChangedOtaFiles} from "./ghw_get_changed_ota_files.js";
|
import {getChangedOtaFiles} from "./ghw_get_changed_ota_files.js";
|
||||||
import {processOtaFiles} from "./ghw_process_ota_files.js";
|
import {processOtaFiles} from "./ghw_process_ota_files.js";
|
||||||
|
|||||||
@@ -1,6 +1,6 @@
|
|||||||
import {readFileSync} from "node:fs";
|
import {readFileSync} from "node:fs";
|
||||||
|
|
||||||
import {UPGRADE_FILE_IDENTIFIER, parseImageHeader} from "./common.js";
|
import {parseImageHeader, UPGRADE_FILE_IDENTIFIER} from "./common.js";
|
||||||
|
|
||||||
const firmwareBuffer = readFileSync(process.argv[2]);
|
const firmwareBuffer = readFileSync(process.argv[2]);
|
||||||
|
|
||||||
|
|||||||
@@ -1,28 +1,25 @@
|
|||||||
import type {ExtraMetas} from "./types";
|
|
||||||
|
|
||||||
import assert from "node:assert";
|
import assert from "node:assert";
|
||||||
import {readFileSync, readdirSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
import {readdirSync, readFileSync, renameSync, rmSync, writeFileSync} from "node:fs";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
|
|
||||||
import {extract} from "tar";
|
import {extract} from "tar";
|
||||||
|
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_DIR,
|
|
||||||
BASE_INDEX_MANIFEST_FILENAME,
|
|
||||||
PREV_IMAGES_DIR,
|
|
||||||
PREV_INDEX_MANIFEST_FILENAME,
|
|
||||||
ParsedImageStatus,
|
|
||||||
TMP_DIR,
|
|
||||||
UPGRADE_FILE_IDENTIFIER,
|
|
||||||
addImageToBase,
|
addImageToBase,
|
||||||
addImageToPrev,
|
addImageToPrev,
|
||||||
|
BASE_IMAGES_DIR,
|
||||||
|
BASE_INDEX_MANIFEST_FILENAME,
|
||||||
findMatchImage,
|
findMatchImage,
|
||||||
getOutDir,
|
getOutDir,
|
||||||
getParsedImageStatus,
|
getParsedImageStatus,
|
||||||
|
ParsedImageStatus,
|
||||||
|
PREV_IMAGES_DIR,
|
||||||
|
PREV_INDEX_MANIFEST_FILENAME,
|
||||||
parseImageHeader,
|
parseImageHeader,
|
||||||
readManifest,
|
readManifest,
|
||||||
|
TMP_DIR,
|
||||||
|
UPGRADE_FILE_IDENTIFIER,
|
||||||
writeManifest,
|
writeManifest,
|
||||||
} from "./common.js";
|
} from "./common.js";
|
||||||
|
import type {ExtraMetas} from "./types";
|
||||||
|
|
||||||
export enum ProcessFirmwareImageStatus {
|
export enum ProcessFirmwareImageStatus {
|
||||||
Error = -1,
|
Error = -1,
|
||||||
|
|||||||
@@ -5,13 +5,11 @@
|
|||||||
*
|
*
|
||||||
*/
|
*/
|
||||||
|
|
||||||
import type {ExtraMetas, RepoImageMeta} from "../src/types";
|
|
||||||
|
|
||||||
import {copyFileSync, existsSync, mkdirSync} from "node:fs";
|
import {copyFileSync, existsSync, mkdirSync} from "node:fs";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
|
|
||||||
import {it} from "vitest";
|
import {it} from "vitest";
|
||||||
import * as common from "../src/common";
|
import * as common from "../src/common";
|
||||||
|
import type {ExtraMetas, RepoImageMeta} from "../src/types";
|
||||||
|
|
||||||
export const IMAGE_V14_1 = "ZLinky_router_v14.ota";
|
export const IMAGE_V14_1 = "ZLinky_router_v14.ota";
|
||||||
export const IMAGE_V14_2 = "ZLinky_router_v14_limited.ota";
|
export const IMAGE_V14_2 = "ZLinky_router_v14_limited.ota";
|
||||||
|
|||||||
@@ -1,18 +1,15 @@
|
|||||||
|
import {existsSync, readFileSync, rmSync} from "node:fs";
|
||||||
|
import path from "node:path";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
import {afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, type MockInstance, vi} from "vitest";
|
||||||
import type {RepoImageMeta} from "../src/types";
|
|
||||||
|
|
||||||
import {existsSync, readFileSync, rmSync} from "node:fs";
|
|
||||||
import path from "node:path";
|
|
||||||
|
|
||||||
import {type MockInstance, afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi} from "vitest";
|
|
||||||
import * as common from "../src/common";
|
import * as common from "../src/common";
|
||||||
import {checkOtaPR} from "../src/ghw_check_ota_pr";
|
import {checkOtaPR} from "../src/ghw_check_ota_pr";
|
||||||
|
import type {RepoImageMeta} from "../src/types";
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_TEST_DIR_PATH,
|
BASE_IMAGES_TEST_DIR_PATH,
|
||||||
IMAGES_TEST_DIR,
|
getAdjustedContent,
|
||||||
IMAGE_INVALID,
|
IMAGE_INVALID,
|
||||||
IMAGE_V12_1,
|
IMAGE_V12_1,
|
||||||
IMAGE_V12_1_METAS,
|
IMAGE_V12_1_METAS,
|
||||||
@@ -25,8 +22,8 @@ import {
|
|||||||
IMAGE_V14_2_COPY,
|
IMAGE_V14_2_COPY,
|
||||||
IMAGE_V14_2_MANUF_METAS,
|
IMAGE_V14_2_MANUF_METAS,
|
||||||
IMAGE_V14_2_METAS,
|
IMAGE_V14_2_METAS,
|
||||||
|
IMAGES_TEST_DIR,
|
||||||
PREV_IMAGES_TEST_DIR_PATH,
|
PREV_IMAGES_TEST_DIR_PATH,
|
||||||
getAdjustedContent,
|
|
||||||
useImage,
|
useImage,
|
||||||
withExtraMetas,
|
withExtraMetas,
|
||||||
} from "./data.test";
|
} from "./data.test";
|
||||||
|
|||||||
@@ -1,12 +1,8 @@
|
|||||||
import type CoreApi from "@actions/core";
|
|
||||||
import type {Context} from "@actions/github/lib/context";
|
|
||||||
|
|
||||||
import type {RepoImageMeta} from "../src/types";
|
|
||||||
|
|
||||||
import {copyFileSync, existsSync, mkdirSync, readFileSync, renameSync, rmSync} from "node:fs";
|
import {copyFileSync, existsSync, mkdirSync, readFileSync, renameSync, rmSync} from "node:fs";
|
||||||
import path from "node:path";
|
import path from "node:path";
|
||||||
|
import type CoreApi from "@actions/core";
|
||||||
import {type MockInstance, afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi} from "vitest";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
|
import {afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, type MockInstance, vi} from "vitest";
|
||||||
import * as common from "../src/common";
|
import * as common from "../src/common";
|
||||||
import {
|
import {
|
||||||
NOT_IN_BASE_MANIFEST_IMAGES_DIR,
|
NOT_IN_BASE_MANIFEST_IMAGES_DIR,
|
||||||
@@ -14,9 +10,11 @@ import {
|
|||||||
NOT_IN_PREV_MANIFEST_IMAGES_DIR,
|
NOT_IN_PREV_MANIFEST_IMAGES_DIR,
|
||||||
reProcessAllImages,
|
reProcessAllImages,
|
||||||
} from "../src/ghw_reprocess_all_images";
|
} from "../src/ghw_reprocess_all_images";
|
||||||
|
import type {RepoImageMeta} from "../src/types";
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_TEST_DIR_PATH,
|
BASE_IMAGES_TEST_DIR_PATH,
|
||||||
IMAGES_TEST_DIR,
|
getAdjustedContent,
|
||||||
|
getImageOriginalDirPath,
|
||||||
IMAGE_INVALID,
|
IMAGE_INVALID,
|
||||||
IMAGE_INVALID_METAS,
|
IMAGE_INVALID_METAS,
|
||||||
IMAGE_V12_1,
|
IMAGE_V12_1,
|
||||||
@@ -24,9 +22,8 @@ import {
|
|||||||
IMAGE_V13_1_METAS,
|
IMAGE_V13_1_METAS,
|
||||||
IMAGE_V14_1,
|
IMAGE_V14_1,
|
||||||
IMAGE_V14_1_METAS,
|
IMAGE_V14_1_METAS,
|
||||||
|
IMAGES_TEST_DIR,
|
||||||
PREV_IMAGES_TEST_DIR_PATH,
|
PREV_IMAGES_TEST_DIR_PATH,
|
||||||
getAdjustedContent,
|
|
||||||
getImageOriginalDirPath,
|
|
||||||
useImage,
|
useImage,
|
||||||
withExtraMetas,
|
withExtraMetas,
|
||||||
} from "./data.test";
|
} from "./data.test";
|
||||||
|
|||||||
@@ -1,21 +1,18 @@
|
|||||||
|
import {rmSync} from "node:fs";
|
||||||
import type CoreApi from "@actions/core";
|
import type CoreApi from "@actions/core";
|
||||||
import type {Context} from "@actions/github/lib/context";
|
import type {Context} from "@actions/github/lib/context";
|
||||||
import type {Octokit} from "@octokit/rest";
|
import type {Octokit} from "@octokit/rest";
|
||||||
|
import {afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, type MockInstance, vi} from "vitest";
|
||||||
import type {RepoImageMeta} from "../src/types";
|
|
||||||
|
|
||||||
import {rmSync} from "node:fs";
|
|
||||||
|
|
||||||
import {type MockInstance, afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi} from "vitest";
|
|
||||||
import * as common from "../src/common";
|
import * as common from "../src/common";
|
||||||
import {updateManifests} from "../src/ghw_update_manifests";
|
import {updateManifests} from "../src/ghw_update_manifests";
|
||||||
|
import type {RepoImageMeta} from "../src/types";
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_TEST_DIR_PATH,
|
BASE_IMAGES_TEST_DIR_PATH,
|
||||||
|
getAdjustedContent,
|
||||||
IMAGE_V13_1,
|
IMAGE_V13_1,
|
||||||
IMAGE_V14_1,
|
IMAGE_V14_1,
|
||||||
IMAGE_V14_1_METAS,
|
IMAGE_V14_1_METAS,
|
||||||
PREV_IMAGES_TEST_DIR_PATH,
|
PREV_IMAGES_TEST_DIR_PATH,
|
||||||
getAdjustedContent,
|
|
||||||
useImage,
|
useImage,
|
||||||
withExtraMetas,
|
withExtraMetas,
|
||||||
} from "./data.test";
|
} from "./data.test";
|
||||||
|
|||||||
@@ -1,13 +1,12 @@
|
|||||||
import type {RepoImageMeta} from "../src/types";
|
|
||||||
|
|
||||||
import {existsSync, mkdirSync, readFileSync, rmSync} from "node:fs";
|
import {existsSync, mkdirSync, readFileSync, rmSync} from "node:fs";
|
||||||
|
import {afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, type MockInstance, vi} from "vitest";
|
||||||
import {type MockInstance, afterAll, afterEach, beforeAll, beforeEach, describe, expect, it, vi} from "vitest";
|
|
||||||
import * as common from "../src/common";
|
import * as common from "../src/common";
|
||||||
import {ProcessFirmwareImageStatus, processFirmwareImage} from "../src/process_firmware_image";
|
import {ProcessFirmwareImageStatus, processFirmwareImage} from "../src/process_firmware_image";
|
||||||
|
import type {RepoImageMeta} from "../src/types";
|
||||||
import {
|
import {
|
||||||
BASE_IMAGES_TEST_DIR_PATH,
|
BASE_IMAGES_TEST_DIR_PATH,
|
||||||
IMAGES_TEST_DIR,
|
getAdjustedContent,
|
||||||
|
getImageOriginalDirPath,
|
||||||
IMAGE_INVALID,
|
IMAGE_INVALID,
|
||||||
IMAGE_TAR,
|
IMAGE_TAR,
|
||||||
IMAGE_TAR_METAS,
|
IMAGE_TAR_METAS,
|
||||||
@@ -17,9 +16,8 @@ import {
|
|||||||
IMAGE_V13_1_METAS,
|
IMAGE_V13_1_METAS,
|
||||||
IMAGE_V14_1,
|
IMAGE_V14_1,
|
||||||
IMAGE_V14_1_METAS,
|
IMAGE_V14_1_METAS,
|
||||||
|
IMAGES_TEST_DIR,
|
||||||
PREV_IMAGES_TEST_DIR_PATH,
|
PREV_IMAGES_TEST_DIR_PATH,
|
||||||
getAdjustedContent,
|
|
||||||
getImageOriginalDirPath,
|
|
||||||
useImage,
|
useImage,
|
||||||
withExtraMetas,
|
withExtraMetas,
|
||||||
} from "./data.test";
|
} from "./data.test";
|
||||||
|
|||||||
@@ -5,5 +5,5 @@
|
|||||||
"rootDir": "..",
|
"rootDir": "..",
|
||||||
"noEmit": true
|
"noEmit": true
|
||||||
},
|
},
|
||||||
"references": [{ "path": ".." }]
|
"references": [{"path": ".."}]
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user