fix(ci): handle non-zfs runner environments gracefully and publish to Gitea packages
CI & Test NaxOS Management API / test (push) Successful in 1m31s
CI & Test NaxOS Management API / test (push) Successful in 1m31s
This commit is contained in:
+31
-16
@@ -1,4 +1,4 @@
|
||||
import { execFile } from 'child_process';
|
||||
import { execFile, execFileSync } from 'child_process';
|
||||
import { promisify } from 'util';
|
||||
import { config } from '../config/index.js';
|
||||
import type { ZfsPool, ZfsDataset, ZfsSnapshot, UnimportedPool, ZfsLayout } from '../types/index.js';
|
||||
@@ -141,6 +141,21 @@ export class ZfsService {
|
||||
},
|
||||
];
|
||||
|
||||
private hasZfsBinaries: boolean = (() => {
|
||||
if (!config.isLinux) return false;
|
||||
try {
|
||||
execFileSync('which', ['zpool'], { stdio: 'ignore' });
|
||||
execFileSync('which', ['zfs'], { stdio: 'ignore' });
|
||||
return true;
|
||||
} catch {
|
||||
return false;
|
||||
}
|
||||
})();
|
||||
|
||||
private get useMock(): boolean {
|
||||
return !this.hasZfsBinaries;
|
||||
}
|
||||
|
||||
private async runCommand(cmd: string, args: string[]): Promise<string> {
|
||||
try {
|
||||
const { stdout } = await execFileAsync(cmd, args);
|
||||
@@ -151,7 +166,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async listPools(): Promise<ZfsPool[]> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
return this.mockPools;
|
||||
}
|
||||
try {
|
||||
@@ -189,7 +204,7 @@ export class ZfsService {
|
||||
ashift?: number;
|
||||
}): Promise<{ success: boolean; message: string }> {
|
||||
const ashift = params.ashift || 12;
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
const newPool: ZfsPool = {
|
||||
name: params.name,
|
||||
size: '19.0T',
|
||||
@@ -230,7 +245,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async scanUnimportedPools(): Promise<UnimportedPool[]> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
return this.mockUnimportedPools;
|
||||
}
|
||||
try {
|
||||
@@ -279,7 +294,7 @@ export class ZfsService {
|
||||
altroot?: string;
|
||||
noMount?: boolean;
|
||||
}): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
const found = this.mockUnimportedPools.find((p) => p.name === params.poolName);
|
||||
if (found) {
|
||||
this.mockUnimportedPools = this.mockUnimportedPools.filter((p) => p.name !== params.poolName);
|
||||
@@ -310,7 +325,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async exportPool(poolName: string): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
this.mockPools = this.mockPools.filter((p) => p.name !== poolName);
|
||||
return { success: true, message: `Pool '${poolName}' exported.` };
|
||||
}
|
||||
@@ -319,7 +334,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async scrub(poolName: string, action: 'start' | 'stop' | 'pause'): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
return { success: true, message: `Scrub ${action} requested for pool '${poolName}'.` };
|
||||
}
|
||||
const flag = action === 'stop' ? '-s' : action === 'pause' ? '-p' : '';
|
||||
@@ -331,7 +346,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async trim(poolName: string): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
return { success: true, message: `TRIM initiated for pool '${poolName}'.` };
|
||||
}
|
||||
await this.runCommand('zpool', ['trim', poolName]);
|
||||
@@ -339,7 +354,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async listDatasets(poolName?: string): Promise<ZfsDataset[]> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
if (poolName) {
|
||||
return this.mockDatasets.filter((d) => d.pool === poolName);
|
||||
}
|
||||
@@ -378,7 +393,7 @@ export class ZfsService {
|
||||
quota?: string;
|
||||
mountpoint?: string;
|
||||
}): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
const pool = params.name.split('/')[0];
|
||||
const newDs: ZfsDataset = {
|
||||
name: params.name,
|
||||
@@ -407,7 +422,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async destroyDataset(name: string, recursive = false): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
this.mockDatasets = this.mockDatasets.filter((d) => d.name !== name && (!recursive || !d.name.startsWith(`${name}/`)));
|
||||
return { success: true, message: `Dataset '${name}' destroyed.` };
|
||||
}
|
||||
@@ -419,7 +434,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async setDatasetProperty(name: string, property: string, value: string): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
const ds = this.mockDatasets.find((d) => d.name === name);
|
||||
if (ds) {
|
||||
(ds as any)[property] = value;
|
||||
@@ -431,7 +446,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async listSnapshots(datasetName?: string): Promise<ZfsSnapshot[]> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
if (datasetName) {
|
||||
return this.mockSnapshots.filter((s) => s.dataset === datasetName);
|
||||
}
|
||||
@@ -461,7 +476,7 @@ export class ZfsService {
|
||||
|
||||
async createSnapshot(datasetName: string, snapshotTag: string): Promise<{ success: boolean; message: string }> {
|
||||
const fullName = `${datasetName}@${snapshotTag}`;
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
this.mockSnapshots.unshift({
|
||||
name: fullName,
|
||||
dataset: datasetName,
|
||||
@@ -477,7 +492,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async rollbackSnapshot(snapshotName: string): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
return { success: true, message: `Dataset rolled back to '${snapshotName}'.` };
|
||||
}
|
||||
await this.runCommand('zfs', ['rollback', '-r', snapshotName]);
|
||||
@@ -485,7 +500,7 @@ export class ZfsService {
|
||||
}
|
||||
|
||||
async destroySnapshot(snapshotName: string): Promise<{ success: boolean; message: string }> {
|
||||
if (!config.isLinux) {
|
||||
if (this.useMock) {
|
||||
this.mockSnapshots = this.mockSnapshots.filter((s) => s.name !== snapshotName);
|
||||
return { success: true, message: `Snapshot '${snapshotName}' destroyed.` };
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user