mirror of
https://github.com/whyour/qinglong.git
synced 2025-05-22 22:36:06 +08:00
QLAPI 支持操作环境变量和系统通知
This commit is contained in:
parent
4667af4ebe
commit
647ed3b66c
|
@ -48,16 +48,18 @@ export default async () => {
|
||||||
} catch (error) {}
|
} catch (error) {}
|
||||||
try {
|
try {
|
||||||
await sequelize.query('alter table Crontabs add column sub_id NUMBER');
|
await sequelize.query('alter table Crontabs add column sub_id NUMBER');
|
||||||
} catch (error) { }
|
} catch (error) {}
|
||||||
try {
|
try {
|
||||||
await sequelize.query('alter table Crontabs add column extra_schedules JSON');
|
await sequelize.query(
|
||||||
} catch (error) { }
|
'alter table Crontabs add column extra_schedules JSON',
|
||||||
|
);
|
||||||
|
} catch (error) {}
|
||||||
try {
|
try {
|
||||||
await sequelize.query('alter table Crontabs add column task_before TEXT');
|
await sequelize.query('alter table Crontabs add column task_before TEXT');
|
||||||
} catch (error) { }
|
} catch (error) {}
|
||||||
try {
|
try {
|
||||||
await sequelize.query('alter table Crontabs add column task_after TEXT');
|
await sequelize.query('alter table Crontabs add column task_after TEXT');
|
||||||
} catch (error) { }
|
} catch (error) {}
|
||||||
|
|
||||||
// 2.10-2.11 升级
|
// 2.10-2.11 升级
|
||||||
const cronDbFile = path.join(config.rootPath, 'db/crontab.db');
|
const cronDbFile = path.join(config.rootPath, 'db/crontab.db');
|
||||||
|
|
|
@ -13,10 +13,11 @@ import { AuthDataType, SystemModel } from '../data/system';
|
||||||
import SystemService from '../services/system';
|
import SystemService from '../services/system';
|
||||||
import UserService from '../services/user';
|
import UserService from '../services/user';
|
||||||
import { writeFile, readFile } from 'fs/promises';
|
import { writeFile, readFile } from 'fs/promises';
|
||||||
import { safeJSONParse } from '../config/util';
|
import { createRandomString, safeJSONParse } from '../config/util';
|
||||||
import OpenService from '../services/open';
|
import OpenService from '../services/open';
|
||||||
import { shareStore } from '../shared/store';
|
import { shareStore } from '../shared/store';
|
||||||
import Logger from './logger';
|
import Logger from './logger';
|
||||||
|
import { AppModel } from '../data/open';
|
||||||
|
|
||||||
export default async () => {
|
export default async () => {
|
||||||
const cronService = Container.get(CronService);
|
const cronService = Container.get(CronService);
|
||||||
|
@ -27,6 +28,19 @@ export default async () => {
|
||||||
const openService = Container.get(OpenService);
|
const openService = Container.get(OpenService);
|
||||||
|
|
||||||
// 初始化增加系统配置
|
// 初始化增加系统配置
|
||||||
|
let systemApp = (
|
||||||
|
await AppModel.findOne({
|
||||||
|
where: { name: 'system' },
|
||||||
|
})
|
||||||
|
)?.get({ plain: true });
|
||||||
|
if (!systemApp) {
|
||||||
|
systemApp = await AppModel.create({
|
||||||
|
name: 'system',
|
||||||
|
scopes: ['crons', 'system'],
|
||||||
|
client_id: createRandomString(12, 12),
|
||||||
|
client_secret: createRandomString(24, 24),
|
||||||
|
});
|
||||||
|
}
|
||||||
const [systemConfig] = await SystemModel.findOrCreate({
|
const [systemConfig] = await SystemModel.findOrCreate({
|
||||||
where: { type: AuthDataType.systemConfig },
|
where: { type: AuthDataType.systemConfig },
|
||||||
});
|
});
|
||||||
|
|
73
back/protos/api.proto
Normal file
73
back/protos/api.proto
Normal file
|
@ -0,0 +1,73 @@
|
||||||
|
syntax = "proto3";
|
||||||
|
|
||||||
|
package com.ql.api;
|
||||||
|
|
||||||
|
message EnvItem {
|
||||||
|
optional int32 id = 1;
|
||||||
|
optional string name = 2;
|
||||||
|
optional string value = 3;
|
||||||
|
optional string remarks = 4;
|
||||||
|
optional int32 status = 5;
|
||||||
|
optional int32 position = 6;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetEnvsRequest { string searchValue = 1; }
|
||||||
|
|
||||||
|
message CreateEnvRequest { repeated EnvItem envs = 1; }
|
||||||
|
|
||||||
|
message UpdateEnvRequest { EnvItem env = 1; }
|
||||||
|
|
||||||
|
message DeleteEnvsRequest { repeated int32 ids = 1; }
|
||||||
|
|
||||||
|
message MoveEnvRequest {
|
||||||
|
int32 id = 1;
|
||||||
|
int32 fromIndex = 2;
|
||||||
|
int32 toIndex = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message DisableEnvsRequest { repeated int32 ids = 1; }
|
||||||
|
|
||||||
|
message EnableEnvsRequest { repeated int32 ids = 1; }
|
||||||
|
|
||||||
|
message UpdateEnvNamesRequest {
|
||||||
|
repeated int32 ids = 1;
|
||||||
|
string name = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message GetEnvByIdRequest { int32 id = 1; }
|
||||||
|
|
||||||
|
message EnvsResponse {
|
||||||
|
int32 code = 1;
|
||||||
|
repeated EnvItem data = 2;
|
||||||
|
optional string message = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message EnvResponse {
|
||||||
|
int32 code = 1;
|
||||||
|
EnvItem data = 2;
|
||||||
|
optional string message = 3;
|
||||||
|
}
|
||||||
|
|
||||||
|
message Response {
|
||||||
|
int32 code = 1;
|
||||||
|
optional string message = 2;
|
||||||
|
}
|
||||||
|
|
||||||
|
message SystemNotifyRequest {
|
||||||
|
string title = 1;
|
||||||
|
string content = 2;
|
||||||
|
}
|
||||||
|
message SystemNotifyResponse {}
|
||||||
|
|
||||||
|
service Api {
|
||||||
|
rpc GetEnvs(GetEnvsRequest) returns (EnvsResponse) {}
|
||||||
|
rpc CreateEnv(CreateEnvRequest) returns (EnvsResponse) {}
|
||||||
|
rpc UpdateEnv(UpdateEnvRequest) returns (EnvResponse) {}
|
||||||
|
rpc DeleteEnvs(DeleteEnvsRequest) returns (Response) {}
|
||||||
|
rpc MoveEnv(MoveEnvRequest) returns (EnvResponse) {}
|
||||||
|
rpc DisableEnvs(DisableEnvsRequest) returns (Response) {}
|
||||||
|
rpc EnableEnvs(EnableEnvsRequest) returns (Response) {}
|
||||||
|
rpc UpdateEnvNames(UpdateEnvNamesRequest) returns (Response) {}
|
||||||
|
rpc GetEnvById(GetEnvByIdRequest) returns (EnvResponse) {}
|
||||||
|
rpc SystemNotify(SystemNotifyRequest) returns (SystemNotifyResponse) {}
|
||||||
|
}
|
1497
back/protos/api.ts
Normal file
1497
back/protos/api.ts
Normal file
File diff suppressed because it is too large
Load Diff
|
@ -1,15 +1,21 @@
|
||||||
|
// Code generated by protoc-gen-ts_proto. DO NOT EDIT.
|
||||||
|
// versions:
|
||||||
|
// protoc-gen-ts_proto v1.181.2
|
||||||
|
// protoc v3.17.3
|
||||||
|
// source: back/protos/cron.proto
|
||||||
|
|
||||||
/* eslint-disable */
|
/* eslint-disable */
|
||||||
import {
|
import {
|
||||||
CallOptions,
|
type CallOptions,
|
||||||
ChannelCredentials,
|
ChannelCredentials,
|
||||||
Client,
|
Client,
|
||||||
ClientOptions,
|
type ClientOptions,
|
||||||
ClientUnaryCall,
|
type ClientUnaryCall,
|
||||||
handleUnaryCall,
|
type handleUnaryCall,
|
||||||
makeGenericClientConstructor,
|
makeGenericClientConstructor,
|
||||||
Metadata,
|
Metadata,
|
||||||
ServiceError,
|
type ServiceError,
|
||||||
UntypedServiceImplementation,
|
type UntypedServiceImplementation,
|
||||||
} from "@grpc/grpc-js";
|
} from "@grpc/grpc-js";
|
||||||
import _m0 from "protobufjs/minimal";
|
import _m0 from "protobufjs/minimal";
|
||||||
|
|
||||||
|
@ -77,19 +83,20 @@ export const ISchedule = {
|
||||||
},
|
},
|
||||||
|
|
||||||
fromJSON(object: any): ISchedule {
|
fromJSON(object: any): ISchedule {
|
||||||
return { schedule: isSet(object.schedule) ? String(object.schedule) : "" };
|
return { schedule: isSet(object.schedule) ? globalThis.String(object.schedule) : "" };
|
||||||
},
|
},
|
||||||
|
|
||||||
toJSON(message: ISchedule): unknown {
|
toJSON(message: ISchedule): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
message.schedule !== undefined && (obj.schedule = message.schedule);
|
if (message.schedule !== "") {
|
||||||
|
obj.schedule = message.schedule;
|
||||||
|
}
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<ISchedule>, I>>(base?: I): ISchedule {
|
create<I extends Exact<DeepPartial<ISchedule>, I>>(base?: I): ISchedule {
|
||||||
return ISchedule.fromPartial(base ?? {});
|
return ISchedule.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<ISchedule>, I>>(object: I): ISchedule {
|
fromPartial<I extends Exact<DeepPartial<ISchedule>, I>>(object: I): ISchedule {
|
||||||
const message = createBaseISchedule();
|
const message = createBaseISchedule();
|
||||||
message.schedule = object.schedule ?? "";
|
message.schedule = object.schedule ?? "";
|
||||||
|
@ -174,34 +181,39 @@ export const ICron = {
|
||||||
|
|
||||||
fromJSON(object: any): ICron {
|
fromJSON(object: any): ICron {
|
||||||
return {
|
return {
|
||||||
id: isSet(object.id) ? String(object.id) : "",
|
id: isSet(object.id) ? globalThis.String(object.id) : "",
|
||||||
schedule: isSet(object.schedule) ? String(object.schedule) : "",
|
schedule: isSet(object.schedule) ? globalThis.String(object.schedule) : "",
|
||||||
command: isSet(object.command) ? String(object.command) : "",
|
command: isSet(object.command) ? globalThis.String(object.command) : "",
|
||||||
extraSchedules: Array.isArray(object?.extraSchedules)
|
extraSchedules: globalThis.Array.isArray(object?.extraSchedules)
|
||||||
? object.extraSchedules.map((e: any) => ISchedule.fromJSON(e))
|
? object.extraSchedules.map((e: any) => ISchedule.fromJSON(e))
|
||||||
: [],
|
: [],
|
||||||
name: isSet(object.name) ? String(object.name) : "",
|
name: isSet(object.name) ? globalThis.String(object.name) : "",
|
||||||
};
|
};
|
||||||
},
|
},
|
||||||
|
|
||||||
toJSON(message: ICron): unknown {
|
toJSON(message: ICron): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
message.id !== undefined && (obj.id = message.id);
|
if (message.id !== "") {
|
||||||
message.schedule !== undefined && (obj.schedule = message.schedule);
|
obj.id = message.id;
|
||||||
message.command !== undefined && (obj.command = message.command);
|
}
|
||||||
if (message.extraSchedules) {
|
if (message.schedule !== "") {
|
||||||
obj.extraSchedules = message.extraSchedules.map((e) => e ? ISchedule.toJSON(e) : undefined);
|
obj.schedule = message.schedule;
|
||||||
} else {
|
}
|
||||||
obj.extraSchedules = [];
|
if (message.command !== "") {
|
||||||
|
obj.command = message.command;
|
||||||
|
}
|
||||||
|
if (message.extraSchedules?.length) {
|
||||||
|
obj.extraSchedules = message.extraSchedules.map((e) => ISchedule.toJSON(e));
|
||||||
|
}
|
||||||
|
if (message.name !== "") {
|
||||||
|
obj.name = message.name;
|
||||||
}
|
}
|
||||||
message.name !== undefined && (obj.name = message.name);
|
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<ICron>, I>>(base?: I): ICron {
|
create<I extends Exact<DeepPartial<ICron>, I>>(base?: I): ICron {
|
||||||
return ICron.fromPartial(base ?? {});
|
return ICron.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<ICron>, I>>(object: I): ICron {
|
fromPartial<I extends Exact<DeepPartial<ICron>, I>>(object: I): ICron {
|
||||||
const message = createBaseICron();
|
const message = createBaseICron();
|
||||||
message.id = object.id ?? "";
|
message.id = object.id ?? "";
|
||||||
|
@ -249,23 +261,20 @@ export const AddCronRequest = {
|
||||||
},
|
},
|
||||||
|
|
||||||
fromJSON(object: any): AddCronRequest {
|
fromJSON(object: any): AddCronRequest {
|
||||||
return { crons: Array.isArray(object?.crons) ? object.crons.map((e: any) => ICron.fromJSON(e)) : [] };
|
return { crons: globalThis.Array.isArray(object?.crons) ? object.crons.map((e: any) => ICron.fromJSON(e)) : [] };
|
||||||
},
|
},
|
||||||
|
|
||||||
toJSON(message: AddCronRequest): unknown {
|
toJSON(message: AddCronRequest): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
if (message.crons) {
|
if (message.crons?.length) {
|
||||||
obj.crons = message.crons.map((e) => e ? ICron.toJSON(e) : undefined);
|
obj.crons = message.crons.map((e) => ICron.toJSON(e));
|
||||||
} else {
|
|
||||||
obj.crons = [];
|
|
||||||
}
|
}
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<AddCronRequest>, I>>(base?: I): AddCronRequest {
|
create<I extends Exact<DeepPartial<AddCronRequest>, I>>(base?: I): AddCronRequest {
|
||||||
return AddCronRequest.fromPartial(base ?? {});
|
return AddCronRequest.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<AddCronRequest>, I>>(object: I): AddCronRequest {
|
fromPartial<I extends Exact<DeepPartial<AddCronRequest>, I>>(object: I): AddCronRequest {
|
||||||
const message = createBaseAddCronRequest();
|
const message = createBaseAddCronRequest();
|
||||||
message.crons = object.crons?.map((e) => ICron.fromPartial(e)) || [];
|
message.crons = object.crons?.map((e) => ICron.fromPartial(e)) || [];
|
||||||
|
@ -308,9 +317,8 @@ export const AddCronResponse = {
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<AddCronResponse>, I>>(base?: I): AddCronResponse {
|
create<I extends Exact<DeepPartial<AddCronResponse>, I>>(base?: I): AddCronResponse {
|
||||||
return AddCronResponse.fromPartial(base ?? {});
|
return AddCronResponse.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<AddCronResponse>, I>>(_: I): AddCronResponse {
|
fromPartial<I extends Exact<DeepPartial<AddCronResponse>, I>>(_: I): AddCronResponse {
|
||||||
const message = createBaseAddCronResponse();
|
const message = createBaseAddCronResponse();
|
||||||
return message;
|
return message;
|
||||||
|
@ -353,23 +361,20 @@ export const DeleteCronRequest = {
|
||||||
},
|
},
|
||||||
|
|
||||||
fromJSON(object: any): DeleteCronRequest {
|
fromJSON(object: any): DeleteCronRequest {
|
||||||
return { ids: Array.isArray(object?.ids) ? object.ids.map((e: any) => String(e)) : [] };
|
return { ids: globalThis.Array.isArray(object?.ids) ? object.ids.map((e: any) => globalThis.String(e)) : [] };
|
||||||
},
|
},
|
||||||
|
|
||||||
toJSON(message: DeleteCronRequest): unknown {
|
toJSON(message: DeleteCronRequest): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
if (message.ids) {
|
if (message.ids?.length) {
|
||||||
obj.ids = message.ids.map((e) => e);
|
obj.ids = message.ids;
|
||||||
} else {
|
|
||||||
obj.ids = [];
|
|
||||||
}
|
}
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<DeleteCronRequest>, I>>(base?: I): DeleteCronRequest {
|
create<I extends Exact<DeepPartial<DeleteCronRequest>, I>>(base?: I): DeleteCronRequest {
|
||||||
return DeleteCronRequest.fromPartial(base ?? {});
|
return DeleteCronRequest.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<DeleteCronRequest>, I>>(object: I): DeleteCronRequest {
|
fromPartial<I extends Exact<DeepPartial<DeleteCronRequest>, I>>(object: I): DeleteCronRequest {
|
||||||
const message = createBaseDeleteCronRequest();
|
const message = createBaseDeleteCronRequest();
|
||||||
message.ids = object.ids?.map((e) => e) || [];
|
message.ids = object.ids?.map((e) => e) || [];
|
||||||
|
@ -412,9 +417,8 @@ export const DeleteCronResponse = {
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<DeleteCronResponse>, I>>(base?: I): DeleteCronResponse {
|
create<I extends Exact<DeepPartial<DeleteCronResponse>, I>>(base?: I): DeleteCronResponse {
|
||||||
return DeleteCronResponse.fromPartial(base ?? {});
|
return DeleteCronResponse.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<DeleteCronResponse>, I>>(_: I): DeleteCronResponse {
|
fromPartial<I extends Exact<DeepPartial<DeleteCronResponse>, I>>(_: I): DeleteCronResponse {
|
||||||
const message = createBaseDeleteCronResponse();
|
const message = createBaseDeleteCronResponse();
|
||||||
return message;
|
return message;
|
||||||
|
@ -484,12 +488,14 @@ export interface CronClient extends Client {
|
||||||
export const CronClient = makeGenericClientConstructor(CronService, "com.ql.cron.Cron") as unknown as {
|
export const CronClient = makeGenericClientConstructor(CronService, "com.ql.cron.Cron") as unknown as {
|
||||||
new (address: string, credentials: ChannelCredentials, options?: Partial<ClientOptions>): CronClient;
|
new (address: string, credentials: ChannelCredentials, options?: Partial<ClientOptions>): CronClient;
|
||||||
service: typeof CronService;
|
service: typeof CronService;
|
||||||
|
serviceName: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
type Builtin = Date | Function | Uint8Array | string | number | boolean | undefined;
|
type Builtin = Date | Function | Uint8Array | string | number | boolean | undefined;
|
||||||
|
|
||||||
export type DeepPartial<T> = T extends Builtin ? T
|
export type DeepPartial<T> = T extends Builtin ? T
|
||||||
: T extends Array<infer U> ? Array<DeepPartial<U>> : T extends ReadonlyArray<infer U> ? ReadonlyArray<DeepPartial<U>>
|
: T extends globalThis.Array<infer U> ? globalThis.Array<DeepPartial<U>>
|
||||||
|
: T extends ReadonlyArray<infer U> ? ReadonlyArray<DeepPartial<U>>
|
||||||
: T extends {} ? { [K in keyof T]?: DeepPartial<T[K]> }
|
: T extends {} ? { [K in keyof T]?: DeepPartial<T[K]> }
|
||||||
: Partial<T>;
|
: Partial<T>;
|
||||||
|
|
||||||
|
|
|
@ -1,17 +1,23 @@
|
||||||
|
// Code generated by protoc-gen-ts_proto. DO NOT EDIT.
|
||||||
|
// versions:
|
||||||
|
// protoc-gen-ts_proto v1.181.2
|
||||||
|
// protoc v3.17.3
|
||||||
|
// source: back/protos/health.proto
|
||||||
|
|
||||||
/* eslint-disable */
|
/* eslint-disable */
|
||||||
import {
|
import {
|
||||||
CallOptions,
|
type CallOptions,
|
||||||
ChannelCredentials,
|
ChannelCredentials,
|
||||||
Client,
|
Client,
|
||||||
ClientOptions,
|
type ClientOptions,
|
||||||
ClientReadableStream,
|
ClientReadableStream,
|
||||||
ClientUnaryCall,
|
type ClientUnaryCall,
|
||||||
handleServerStreamingCall,
|
handleServerStreamingCall,
|
||||||
handleUnaryCall,
|
type handleUnaryCall,
|
||||||
makeGenericClientConstructor,
|
makeGenericClientConstructor,
|
||||||
Metadata,
|
Metadata,
|
||||||
ServiceError,
|
type ServiceError,
|
||||||
UntypedServiceImplementation,
|
type UntypedServiceImplementation,
|
||||||
} from "@grpc/grpc-js";
|
} from "@grpc/grpc-js";
|
||||||
import _m0 from "protobufjs/minimal";
|
import _m0 from "protobufjs/minimal";
|
||||||
|
|
||||||
|
@ -106,19 +112,20 @@ export const HealthCheckRequest = {
|
||||||
},
|
},
|
||||||
|
|
||||||
fromJSON(object: any): HealthCheckRequest {
|
fromJSON(object: any): HealthCheckRequest {
|
||||||
return { service: isSet(object.service) ? String(object.service) : "" };
|
return { service: isSet(object.service) ? globalThis.String(object.service) : "" };
|
||||||
},
|
},
|
||||||
|
|
||||||
toJSON(message: HealthCheckRequest): unknown {
|
toJSON(message: HealthCheckRequest): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
message.service !== undefined && (obj.service = message.service);
|
if (message.service !== "") {
|
||||||
|
obj.service = message.service;
|
||||||
|
}
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<HealthCheckRequest>, I>>(base?: I): HealthCheckRequest {
|
create<I extends Exact<DeepPartial<HealthCheckRequest>, I>>(base?: I): HealthCheckRequest {
|
||||||
return HealthCheckRequest.fromPartial(base ?? {});
|
return HealthCheckRequest.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<HealthCheckRequest>, I>>(object: I): HealthCheckRequest {
|
fromPartial<I extends Exact<DeepPartial<HealthCheckRequest>, I>>(object: I): HealthCheckRequest {
|
||||||
const message = createBaseHealthCheckRequest();
|
const message = createBaseHealthCheckRequest();
|
||||||
message.service = object.service ?? "";
|
message.service = object.service ?? "";
|
||||||
|
@ -167,14 +174,15 @@ export const HealthCheckResponse = {
|
||||||
|
|
||||||
toJSON(message: HealthCheckResponse): unknown {
|
toJSON(message: HealthCheckResponse): unknown {
|
||||||
const obj: any = {};
|
const obj: any = {};
|
||||||
message.status !== undefined && (obj.status = healthCheckResponse_ServingStatusToJSON(message.status));
|
if (message.status !== 0) {
|
||||||
|
obj.status = healthCheckResponse_ServingStatusToJSON(message.status);
|
||||||
|
}
|
||||||
return obj;
|
return obj;
|
||||||
},
|
},
|
||||||
|
|
||||||
create<I extends Exact<DeepPartial<HealthCheckResponse>, I>>(base?: I): HealthCheckResponse {
|
create<I extends Exact<DeepPartial<HealthCheckResponse>, I>>(base?: I): HealthCheckResponse {
|
||||||
return HealthCheckResponse.fromPartial(base ?? {});
|
return HealthCheckResponse.fromPartial(base ?? ({} as any));
|
||||||
},
|
},
|
||||||
|
|
||||||
fromPartial<I extends Exact<DeepPartial<HealthCheckResponse>, I>>(object: I): HealthCheckResponse {
|
fromPartial<I extends Exact<DeepPartial<HealthCheckResponse>, I>>(object: I): HealthCheckResponse {
|
||||||
const message = createBaseHealthCheckResponse();
|
const message = createBaseHealthCheckResponse();
|
||||||
message.status = object.status ?? 0;
|
message.status = object.status ?? 0;
|
||||||
|
@ -236,12 +244,14 @@ export interface HealthClient extends Client {
|
||||||
export const HealthClient = makeGenericClientConstructor(HealthService, "com.ql.health.Health") as unknown as {
|
export const HealthClient = makeGenericClientConstructor(HealthService, "com.ql.health.Health") as unknown as {
|
||||||
new (address: string, credentials: ChannelCredentials, options?: Partial<ClientOptions>): HealthClient;
|
new (address: string, credentials: ChannelCredentials, options?: Partial<ClientOptions>): HealthClient;
|
||||||
service: typeof HealthService;
|
service: typeof HealthService;
|
||||||
|
serviceName: string;
|
||||||
};
|
};
|
||||||
|
|
||||||
type Builtin = Date | Function | Uint8Array | string | number | boolean | undefined;
|
type Builtin = Date | Function | Uint8Array | string | number | boolean | undefined;
|
||||||
|
|
||||||
export type DeepPartial<T> = T extends Builtin ? T
|
export type DeepPartial<T> = T extends Builtin ? T
|
||||||
: T extends Array<infer U> ? Array<DeepPartial<U>> : T extends ReadonlyArray<infer U> ? ReadonlyArray<DeepPartial<U>>
|
: T extends globalThis.Array<infer U> ? globalThis.Array<DeepPartial<U>>
|
||||||
|
: T extends ReadonlyArray<infer U> ? ReadonlyArray<DeepPartial<U>>
|
||||||
: T extends {} ? { [K in keyof T]?: DeepPartial<T[K]> }
|
: T extends {} ? { [K in keyof T]?: DeepPartial<T[K]> }
|
||||||
: Partial<T>;
|
: Partial<T>;
|
||||||
|
|
||||||
|
|
171
back/schedule/api.ts
Normal file
171
back/schedule/api.ts
Normal file
|
@ -0,0 +1,171 @@
|
||||||
|
import 'reflect-metadata';
|
||||||
|
import { Container } from 'typedi';
|
||||||
|
import EnvService from '../services/env';
|
||||||
|
import { sendUnaryData, ServerUnaryCall } from '@grpc/grpc-js';
|
||||||
|
import {
|
||||||
|
CreateEnvRequest,
|
||||||
|
DeleteEnvsRequest,
|
||||||
|
DisableEnvsRequest,
|
||||||
|
EnableEnvsRequest,
|
||||||
|
EnvItem,
|
||||||
|
EnvResponse,
|
||||||
|
EnvsResponse,
|
||||||
|
GetEnvByIdRequest,
|
||||||
|
GetEnvsRequest,
|
||||||
|
MoveEnvRequest,
|
||||||
|
Response,
|
||||||
|
SystemNotifyRequest,
|
||||||
|
SystemNotifyResponse,
|
||||||
|
UpdateEnvNamesRequest,
|
||||||
|
UpdateEnvRequest,
|
||||||
|
} from '../protos/api';
|
||||||
|
import LoggerInstance from '../loaders/logger';
|
||||||
|
import NotificationService from '../services/notify';
|
||||||
|
|
||||||
|
Container.set('logger', LoggerInstance);
|
||||||
|
|
||||||
|
export const getEnvs = async (
|
||||||
|
call: ServerUnaryCall<GetEnvsRequest, EnvsResponse>,
|
||||||
|
callback: sendUnaryData<EnvsResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
const data = await envService.envs(call.request.searchValue);
|
||||||
|
callback(null, {
|
||||||
|
code: 200,
|
||||||
|
data: data.map((x) => ({ ...x, remarks: x.remarks || '' })),
|
||||||
|
});
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(null, {
|
||||||
|
code: 500,
|
||||||
|
data: [],
|
||||||
|
message: e.message,
|
||||||
|
});
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const createEnv = async (
|
||||||
|
call: ServerUnaryCall<CreateEnvRequest, EnvsResponse>,
|
||||||
|
callback: sendUnaryData<EnvsResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
const data = await envService.create(call.request.envs);
|
||||||
|
callback(null, { code: 200, data });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const updateEnv = async (
|
||||||
|
call: ServerUnaryCall<UpdateEnvRequest, EnvResponse>,
|
||||||
|
callback: sendUnaryData<EnvResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
const data = await envService.update(call.request.env as EnvItem);
|
||||||
|
callback(null, { code: 200, data });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const deleteEnvs = async (
|
||||||
|
call: ServerUnaryCall<DeleteEnvsRequest, Response>,
|
||||||
|
callback: sendUnaryData<Response>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
await envService.remove(call.request.ids);
|
||||||
|
callback(null, { code: 200 });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const moveEnv = async (
|
||||||
|
call: ServerUnaryCall<MoveEnvRequest, EnvResponse>,
|
||||||
|
callback: sendUnaryData<EnvResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
const data = await envService.move(call.request.id, {
|
||||||
|
fromIndex: call.request.fromIndex,
|
||||||
|
toIndex: call.request.toIndex,
|
||||||
|
});
|
||||||
|
callback(null, { code: 200, data });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const disableEnvs = async (
|
||||||
|
call: ServerUnaryCall<DisableEnvsRequest, Response>,
|
||||||
|
callback: sendUnaryData<Response>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
await envService.disabled(call.request.ids);
|
||||||
|
callback(null, { code: 200 });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const enableEnvs = async (
|
||||||
|
call: ServerUnaryCall<EnableEnvsRequest, Response>,
|
||||||
|
callback: sendUnaryData<Response>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
await envService.enabled(call.request.ids);
|
||||||
|
callback(null, { code: 200 });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const updateEnvNames = async (
|
||||||
|
call: ServerUnaryCall<UpdateEnvNamesRequest, Response>,
|
||||||
|
callback: sendUnaryData<Response>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
await envService.updateNames({
|
||||||
|
ids: call.request.ids,
|
||||||
|
name: call.request.name,
|
||||||
|
});
|
||||||
|
callback(null, { code: 200 });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const getEnvById = async (
|
||||||
|
call: ServerUnaryCall<GetEnvByIdRequest, EnvResponse>,
|
||||||
|
callback: sendUnaryData<EnvResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const envService = Container.get(EnvService);
|
||||||
|
const data = await envService.getDb({ id: call.request.id });
|
||||||
|
callback(null, { code: 200, data });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
||||||
|
|
||||||
|
export const systemNotify = async (
|
||||||
|
call: ServerUnaryCall<SystemNotifyRequest, SystemNotifyResponse>,
|
||||||
|
callback: sendUnaryData<SystemNotifyResponse>,
|
||||||
|
) => {
|
||||||
|
try {
|
||||||
|
const notifyService = Container.get(NotificationService);
|
||||||
|
const data = await notifyService.notify(
|
||||||
|
call.request.title,
|
||||||
|
call.request.content,
|
||||||
|
);
|
||||||
|
callback(null, { code: 200, data });
|
||||||
|
} catch (e: any) {
|
||||||
|
callback(e);
|
||||||
|
}
|
||||||
|
};
|
|
@ -6,10 +6,13 @@ import { HealthService } from '../protos/health';
|
||||||
import { check } from './health';
|
import { check } from './health';
|
||||||
import config from '../config';
|
import config from '../config';
|
||||||
import Logger from '../loaders/logger';
|
import Logger from '../loaders/logger';
|
||||||
|
import { ApiService } from '../protos/api';
|
||||||
|
import * as Api from './api';
|
||||||
|
|
||||||
const server = new Server({ 'grpc.enable_http_proxy': 0 });
|
const server = new Server({ 'grpc.enable_http_proxy': 0 });
|
||||||
server.addService(HealthService, { check });
|
server.addService(HealthService, { check });
|
||||||
server.addService(CronService, { addCron, delCron });
|
server.addService(CronService, { addCron, delCron });
|
||||||
|
server.addService(ApiService, Api);
|
||||||
server.bindAsync(
|
server.bindAsync(
|
||||||
`0.0.0.0:${config.cronPort}`,
|
`0.0.0.0:${config.cronPort}`,
|
||||||
ServerCredentials.createInsecure(),
|
ServerCredentials.createInsecure(),
|
||||||
|
|
|
@ -62,7 +62,7 @@ export default class EnvService {
|
||||||
return await this.getDb({ id: payload.id });
|
return await this.getDb({ id: payload.id });
|
||||||
}
|
}
|
||||||
|
|
||||||
public async remove(ids: string[]) {
|
public async remove(ids: number[]) {
|
||||||
await EnvModel.destroy({ where: { id: ids } });
|
await EnvModel.destroy({ where: { id: ids } });
|
||||||
await this.set_envs();
|
await this.set_envs();
|
||||||
}
|
}
|
||||||
|
@ -150,7 +150,7 @@ export default class EnvService {
|
||||||
['position', 'DESC'],
|
['position', 'DESC'],
|
||||||
['createdAt', 'ASC'],
|
['createdAt', 'ASC'],
|
||||||
]);
|
]);
|
||||||
return result as any;
|
return result;
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
throw error;
|
throw error;
|
||||||
}
|
}
|
||||||
|
@ -161,7 +161,7 @@ export default class EnvService {
|
||||||
where: { ...query },
|
where: { ...query },
|
||||||
order: [...sort],
|
order: [...sort],
|
||||||
});
|
});
|
||||||
return docs;
|
return docs.map((x) => x.get({ plain: true }));
|
||||||
}
|
}
|
||||||
|
|
||||||
public async getDb(query: FindOptions<Env>['where']): Promise<Env> {
|
public async getDb(query: FindOptions<Env>['where']): Promise<Env> {
|
||||||
|
@ -172,7 +172,7 @@ export default class EnvService {
|
||||||
return doc.get({ plain: true });
|
return doc.get({ plain: true });
|
||||||
}
|
}
|
||||||
|
|
||||||
public async disabled(ids: string[]) {
|
public async disabled(ids: number[]) {
|
||||||
await EnvModel.update(
|
await EnvModel.update(
|
||||||
{ status: EnvStatus.disabled },
|
{ status: EnvStatus.disabled },
|
||||||
{ where: { id: ids } },
|
{ where: { id: ids } },
|
||||||
|
@ -180,12 +180,12 @@ export default class EnvService {
|
||||||
await this.set_envs();
|
await this.set_envs();
|
||||||
}
|
}
|
||||||
|
|
||||||
public async enabled(ids: string[]) {
|
public async enabled(ids: number[]) {
|
||||||
await EnvModel.update({ status: EnvStatus.normal }, { where: { id: ids } });
|
await EnvModel.update({ status: EnvStatus.normal }, { where: { id: ids } });
|
||||||
await this.set_envs();
|
await this.set_envs();
|
||||||
}
|
}
|
||||||
|
|
||||||
public async updateNames({ ids, name }: { ids: string[]; name: string }) {
|
public async updateNames({ ids, name }: { ids: number[]; name: string }) {
|
||||||
await EnvModel.update({ name }, { where: { id: ids } });
|
await EnvModel.update({ name }, { where: { id: ids } });
|
||||||
await this.set_envs();
|
await this.set_envs();
|
||||||
}
|
}
|
||||||
|
|
|
@ -159,16 +159,15 @@ export default class OpenService {
|
||||||
value: string;
|
value: string;
|
||||||
expiration: number;
|
expiration: number;
|
||||||
}> {
|
}> {
|
||||||
let systemApp = (
|
const apps = await shareStore.getApps();
|
||||||
await AppModel.findOne({
|
const systemApp = apps?.find((x) => x.name === 'system');
|
||||||
where: { name: 'system' },
|
|
||||||
})
|
|
||||||
)?.get({ plain: true });
|
|
||||||
if (!systemApp) {
|
if (!systemApp) {
|
||||||
systemApp = await this.create({
|
throw new Error('system app not found');
|
||||||
name: 'system',
|
}
|
||||||
scopes: ['crons', 'system'],
|
const now = Math.round(Date.now() / 1000);
|
||||||
} as App);
|
const currentToken = systemApp.tokens?.find((x) => x.expiration > now);
|
||||||
|
if (currentToken) {
|
||||||
|
return currentToken;
|
||||||
}
|
}
|
||||||
const { data } = await this.authToken({
|
const { data } = await this.authToken({
|
||||||
client_id: systemApp.client_id,
|
client_id: systemApp.client_id,
|
||||||
|
|
|
@ -14,6 +14,7 @@
|
||||||
"public": "npm run build:back && node static/build/public.js",
|
"public": "npm run build:back && node static/build/public.js",
|
||||||
"update": "npm run build:back && node static/build/update.js",
|
"update": "npm run build:back && node static/build/update.js",
|
||||||
"gen:proto": "protoc --experimental_allow_proto3_optional --plugin=./node_modules/.bin/protoc-gen-ts_proto ./back/protos/*.proto --ts_proto_out=./ --ts_proto_opt=outputServices=grpc-js,env=node,esModuleInterop=true",
|
"gen:proto": "protoc --experimental_allow_proto3_optional --plugin=./node_modules/.bin/protoc-gen-ts_proto ./back/protos/*.proto --ts_proto_out=./ --ts_proto_opt=outputServices=grpc-js,env=node,esModuleInterop=true",
|
||||||
|
"gen:api": "python3 -m grpc_tools.protoc -I. --python_out=. --grpc_python_out=. ./back/protos/api.proto",
|
||||||
"prettier": "prettier --write '**/*.{js,jsx,tsx,ts,less,md,json}'",
|
"prettier": "prettier --write '**/*.{js,jsx,tsx,ts,less,md,json}'",
|
||||||
"postinstall": "max setup 2>/dev/null || true",
|
"postinstall": "max setup 2>/dev/null || true",
|
||||||
"test": "umi-test",
|
"test": "umi-test",
|
||||||
|
@ -61,6 +62,7 @@
|
||||||
},
|
},
|
||||||
"dependencies": {
|
"dependencies": {
|
||||||
"@grpc/grpc-js": "^1.12.3",
|
"@grpc/grpc-js": "^1.12.3",
|
||||||
|
"@grpc/proto-loader": "^0.7.13",
|
||||||
"@otplib/preset-default": "^12.0.1",
|
"@otplib/preset-default": "^12.0.1",
|
||||||
"@sentry/node": "^8.42.0",
|
"@sentry/node": "^8.42.0",
|
||||||
"body-parser": "^1.20.3",
|
"body-parser": "^1.20.3",
|
||||||
|
|
|
@ -11,6 +11,9 @@ dependencies:
|
||||||
'@grpc/grpc-js':
|
'@grpc/grpc-js':
|
||||||
specifier: ^1.12.3
|
specifier: ^1.12.3
|
||||||
version: 1.12.3
|
version: 1.12.3
|
||||||
|
'@grpc/proto-loader':
|
||||||
|
specifier: ^0.7.13
|
||||||
|
version: 0.7.13
|
||||||
'@keyv/sqlite':
|
'@keyv/sqlite':
|
||||||
specifier: ^4.0.1
|
specifier: ^4.0.1
|
||||||
version: 4.0.1
|
version: 4.0.1
|
||||||
|
|
|
@ -6,4 +6,10 @@
|
||||||
*/
|
*/
|
||||||
console.log('test scripts');
|
console.log('test scripts');
|
||||||
QLAPI.notify('test scripts', 'test desc');
|
QLAPI.notify('test scripts', 'test desc');
|
||||||
|
QLAPI.getEnvs({ searchValue: 'dddd' }).then(x => {
|
||||||
|
console.log(x)
|
||||||
|
})
|
||||||
|
QLAPI.systemNotify({ title: '123', content: '231' }).then(x => {
|
||||||
|
console.log(x)
|
||||||
|
})
|
||||||
console.log('test desc');
|
console.log('test desc');
|
||||||
|
|
|
@ -4,6 +4,9 @@ name: script name
|
||||||
定时规则
|
定时规则
|
||||||
cron: 1 9 * * *
|
cron: 1 9 * * *
|
||||||
"""
|
"""
|
||||||
|
|
||||||
print("test script")
|
print("test script")
|
||||||
QLAPI.notify('test script', 'test desc')
|
QLAPI.notify("test script", "test desc")
|
||||||
|
QLAPI.systemNotify({"title": "test script", "content": "dddd"})
|
||||||
|
print(QLAPI.getEnvs("1"))
|
||||||
print("test desc")
|
print("test desc")
|
||||||
|
|
46
shell/preload/client.js
Normal file
46
shell/preload/client.js
Normal file
|
@ -0,0 +1,46 @@
|
||||||
|
const grpc = require('@grpc/grpc-js');
|
||||||
|
const protoLoader = require('@grpc/proto-loader');
|
||||||
|
const path = require('path');
|
||||||
|
|
||||||
|
const PROTO_PATH = path.resolve(__dirname, '../../back/protos/api.proto');
|
||||||
|
const options = {
|
||||||
|
keepCase: true,
|
||||||
|
longs: String,
|
||||||
|
enums: String,
|
||||||
|
defaults: true,
|
||||||
|
};
|
||||||
|
|
||||||
|
const packageDefinition = protoLoader.loadSync(PROTO_PATH, options);
|
||||||
|
const apiProto = grpc.loadPackageDefinition(packageDefinition).com.ql.api;
|
||||||
|
|
||||||
|
const client = new apiProto.Api(
|
||||||
|
`0.0.0.0:5500`,
|
||||||
|
grpc.credentials.createInsecure(),
|
||||||
|
{ 'grpc.enable_http_proxy': 0 },
|
||||||
|
);
|
||||||
|
|
||||||
|
const promisify = (fn) => {
|
||||||
|
return (...args) => {
|
||||||
|
return new Promise((resolve, reject) => {
|
||||||
|
fn.call(client, ...args, (err, response) => {
|
||||||
|
if (err) return reject(err);
|
||||||
|
resolve(response);
|
||||||
|
});
|
||||||
|
});
|
||||||
|
};
|
||||||
|
};
|
||||||
|
|
||||||
|
const api = {
|
||||||
|
getEnvs: promisify(client.GetEnvs),
|
||||||
|
createEnv: promisify(client.CreateEnv),
|
||||||
|
updateEnv: promisify(client.UpdateEnv),
|
||||||
|
deleteEnvs: promisify(client.DeleteEnvs),
|
||||||
|
moveEnv: promisify(client.MoveEnv),
|
||||||
|
disableEnvs: promisify(client.DisableEnvs),
|
||||||
|
enableEnvs: promisify(client.EnableEnvs),
|
||||||
|
updateEnvNames: promisify(client.UpdateEnvNames),
|
||||||
|
getEnvById: promisify(client.GetEnvById),
|
||||||
|
systemNotify: promisify(client.SystemNotify),
|
||||||
|
};
|
||||||
|
|
||||||
|
module.exports = api;
|
113
shell/preload/client.py
Normal file
113
shell/preload/client.py
Normal file
|
@ -0,0 +1,113 @@
|
||||||
|
import subprocess
|
||||||
|
import json
|
||||||
|
import tempfile
|
||||||
|
import os
|
||||||
|
from typing import Dict, List
|
||||||
|
from functools import wraps
|
||||||
|
|
||||||
|
|
||||||
|
def error_handler(func):
|
||||||
|
@wraps(func)
|
||||||
|
def wrapper(*args, **kwargs):
|
||||||
|
try:
|
||||||
|
return func(*args, **kwargs)
|
||||||
|
except json.JSONDecodeError as e:
|
||||||
|
raise Exception(f"parse json error: {str(e)}")
|
||||||
|
except subprocess.SubprocessError as e:
|
||||||
|
raise Exception(f"node process error: {str(e)}")
|
||||||
|
except Exception as e:
|
||||||
|
raise Exception(f"unknown error: {str(e)}")
|
||||||
|
|
||||||
|
return wrapper
|
||||||
|
|
||||||
|
|
||||||
|
class Client:
|
||||||
|
def __init__(self):
|
||||||
|
self.temp_dir = tempfile.mkdtemp(prefix="node_client_")
|
||||||
|
self.temp_script = os.path.join(self.temp_dir, "temp_script.js")
|
||||||
|
|
||||||
|
def __del__(self):
|
||||||
|
try:
|
||||||
|
if os.path.exists(self.temp_script):
|
||||||
|
os.remove(self.temp_script)
|
||||||
|
os.rmdir(self.temp_dir)
|
||||||
|
except Exception:
|
||||||
|
pass
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def _execute_node(self, method: str, params: Dict = None) -> Dict:
|
||||||
|
node_code = f"""
|
||||||
|
const api = require('{os.getenv("QL_DIR")}/shell/preload/client.js');
|
||||||
|
|
||||||
|
(async () => {{
|
||||||
|
try {{
|
||||||
|
const result = await api.{method}({json.dumps(params) if params else ''});
|
||||||
|
console.log(JSON.stringify(result));
|
||||||
|
}} catch (error) {{
|
||||||
|
console.error(JSON.stringify({{
|
||||||
|
error: error.message,
|
||||||
|
stack: error.stack
|
||||||
|
}}));
|
||||||
|
process.exit(1);
|
||||||
|
}}
|
||||||
|
}})();
|
||||||
|
"""
|
||||||
|
|
||||||
|
with open(self.temp_script, "w", encoding="utf-8") as f:
|
||||||
|
f.write(node_code)
|
||||||
|
|
||||||
|
try:
|
||||||
|
result = subprocess.run(
|
||||||
|
["node", self.temp_script],
|
||||||
|
capture_output=True,
|
||||||
|
text=True,
|
||||||
|
timeout=30,
|
||||||
|
)
|
||||||
|
|
||||||
|
if result.returncode != 0:
|
||||||
|
error_data = json.loads(result.stderr)
|
||||||
|
raise Exception(f"{error_data.get('stack')}")
|
||||||
|
|
||||||
|
return json.loads(result.stdout)
|
||||||
|
except subprocess.TimeoutExpired:
|
||||||
|
raise Exception("node process timeout")
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def getEnvs(self, params: Dict = None) -> Dict:
|
||||||
|
return self._execute_node("getEnvs", params)
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def createEnv(self, data: Dict) -> Dict:
|
||||||
|
return self._execute_node("createEnv", data)
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def updateEnv(self, data: Dict) -> Dict:
|
||||||
|
return self._execute_node("updateEnv", data)
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def deleteEnvs(self, env_ids: List[str]) -> Dict:
|
||||||
|
return self._execute_node("deleteEnvs", {"ids": env_ids})
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def moveEnv(self, data: Dict) -> Dict:
|
||||||
|
return self._execute_node("moveEnv", data)
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def disableEnvs(self, env_ids: List[str]) -> Dict:
|
||||||
|
return self._execute_node("disableEnvs", {"ids": env_ids})
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def enableEnvs(self, env_ids: List[str]) -> Dict:
|
||||||
|
return self._execute_node("enableEnvs", {"ids": env_ids})
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def updateEnvNames(self, data: Dict) -> Dict:
|
||||||
|
return self._execute_node("updateEnvNames", data)
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def getEnvById(self, env_id: str) -> Dict:
|
||||||
|
return self._execute_node("getEnvById", {"id": env_id})
|
||||||
|
|
||||||
|
@error_handler
|
||||||
|
def systemNotify(self, data: Dict) -> Dict:
|
||||||
|
return self._execute_node("systemNotify", data)
|
|
@ -1,4 +1,5 @@
|
||||||
const { execSync } = require('child_process');
|
const { execSync } = require('child_process');
|
||||||
|
const client = require('./client.js');
|
||||||
require(`./env.js`);
|
require(`./env.js`);
|
||||||
|
|
||||||
function expandRange(rangeStr, max) {
|
function expandRange(rangeStr, max) {
|
||||||
|
@ -100,6 +101,7 @@ try {
|
||||||
const { sendNotify } = require('./notify.js');
|
const { sendNotify } = require('./notify.js');
|
||||||
global.QLAPI = {
|
global.QLAPI = {
|
||||||
notify: sendNotify,
|
notify: sendNotify,
|
||||||
|
...client,
|
||||||
};
|
};
|
||||||
} catch (error) {
|
} catch (error) {
|
||||||
console.log(`run builtin code error: `, error, '\n');
|
console.log(`run builtin code error: `, error, '\n');
|
||||||
|
|
|
@ -6,6 +6,7 @@ import builtins
|
||||||
import sys
|
import sys
|
||||||
import env
|
import env
|
||||||
import signal
|
import signal
|
||||||
|
from client import Client
|
||||||
|
|
||||||
|
|
||||||
def try_parse_int(value):
|
def try_parse_int(value):
|
||||||
|
@ -108,7 +109,7 @@ try:
|
||||||
|
|
||||||
from notify import send
|
from notify import send
|
||||||
|
|
||||||
class BaseApi:
|
class BaseApi(Client):
|
||||||
def notify(self, *args, **kwargs):
|
def notify(self, *args, **kwargs):
|
||||||
return send(*args, **kwargs)
|
return send(*args, **kwargs)
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user