Use query builder to get projects without deployments
All checks were successful
Lint / lint (20.x) (pull_request) Successful in 4m13s
All checks were successful
Lint / lint (20.x) (pull_request) Successful in 4m13s
This commit is contained in:
parent
1bd28e0309
commit
83819fc211
@ -33,7 +33,7 @@ export class Database {
|
|||||||
private dataSource: DataSource;
|
private dataSource: DataSource;
|
||||||
private projectDomain: string;
|
private projectDomain: string;
|
||||||
|
|
||||||
constructor ({ dbPath } : DatabaseConfig, { projectDomain } : MiscConfig) {
|
constructor({ dbPath }: DatabaseConfig, { projectDomain }: MiscConfig) {
|
||||||
this.dataSource = new DataSource({
|
this.dataSource = new DataSource({
|
||||||
type: 'better-sqlite3',
|
type: 'better-sqlite3',
|
||||||
database: dbPath,
|
database: dbPath,
|
||||||
@ -45,7 +45,7 @@ export class Database {
|
|||||||
this.projectDomain = projectDomain;
|
this.projectDomain = projectDomain;
|
||||||
}
|
}
|
||||||
|
|
||||||
async init (): Promise<void> {
|
async init(): Promise<void> {
|
||||||
await this.dataSource.initialize();
|
await this.dataSource.initialize();
|
||||||
log('database initialized');
|
log('database initialized');
|
||||||
|
|
||||||
@ -58,21 +58,21 @@ export class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async getUser (options: FindOneOptions<User>): Promise<User | null> {
|
async getUser(options: FindOneOptions<User>): Promise<User | null> {
|
||||||
const userRepository = this.dataSource.getRepository(User);
|
const userRepository = this.dataSource.getRepository(User);
|
||||||
const user = await userRepository.findOne(options);
|
const user = await userRepository.findOne(options);
|
||||||
|
|
||||||
return user;
|
return user;
|
||||||
}
|
}
|
||||||
|
|
||||||
async addUser (data: DeepPartial<User>): Promise<User> {
|
async addUser(data: DeepPartial<User>): Promise<User> {
|
||||||
const userRepository = this.dataSource.getRepository(User);
|
const userRepository = this.dataSource.getRepository(User);
|
||||||
const user = await userRepository.save(data);
|
const user = await userRepository.save(data);
|
||||||
|
|
||||||
return user;
|
return user;
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateUser (user: User, data: DeepPartial<User>): Promise<boolean> {
|
async updateUser(user: User, data: DeepPartial<User>): Promise<boolean> {
|
||||||
const userRepository = this.dataSource.getRepository(User);
|
const userRepository = this.dataSource.getRepository(User);
|
||||||
const updateResult = await userRepository.update({ id: user.id }, data);
|
const updateResult = await userRepository.update({ id: user.id }, data);
|
||||||
assert(updateResult.affected);
|
assert(updateResult.affected);
|
||||||
@ -80,7 +80,7 @@ export class Database {
|
|||||||
return updateResult.affected > 0;
|
return updateResult.affected > 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getOrganizations (
|
async getOrganizations(
|
||||||
options: FindManyOptions<Organization>
|
options: FindManyOptions<Organization>
|
||||||
): Promise<Organization[]> {
|
): Promise<Organization[]> {
|
||||||
const organizationRepository = this.dataSource.getRepository(Organization);
|
const organizationRepository = this.dataSource.getRepository(Organization);
|
||||||
@ -89,7 +89,7 @@ export class Database {
|
|||||||
return organizations;
|
return organizations;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getOrganization (
|
async getOrganization(
|
||||||
options: FindOneOptions<Organization>
|
options: FindOneOptions<Organization>
|
||||||
): Promise<Organization | null> {
|
): Promise<Organization | null> {
|
||||||
const organizationRepository = this.dataSource.getRepository(Organization);
|
const organizationRepository = this.dataSource.getRepository(Organization);
|
||||||
@ -98,7 +98,7 @@ export class Database {
|
|||||||
return organization;
|
return organization;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getOrganizationsByUserId (userId: string): Promise<Organization[]> {
|
async getOrganizationsByUserId(userId: string): Promise<Organization[]> {
|
||||||
const organizationRepository = this.dataSource.getRepository(Organization);
|
const organizationRepository = this.dataSource.getRepository(Organization);
|
||||||
|
|
||||||
const userOrgs = await organizationRepository.find({
|
const userOrgs = await organizationRepository.find({
|
||||||
@ -114,21 +114,21 @@ export class Database {
|
|||||||
return userOrgs;
|
return userOrgs;
|
||||||
}
|
}
|
||||||
|
|
||||||
async addUserOrganization (data: DeepPartial<UserOrganization>): Promise<UserOrganization> {
|
async addUserOrganization(data: DeepPartial<UserOrganization>): Promise<UserOrganization> {
|
||||||
const userOrganizationRepository = this.dataSource.getRepository(UserOrganization);
|
const userOrganizationRepository = this.dataSource.getRepository(UserOrganization);
|
||||||
const newUserOrganization = await userOrganizationRepository.save(data);
|
const newUserOrganization = await userOrganizationRepository.save(data);
|
||||||
|
|
||||||
return newUserOrganization;
|
return newUserOrganization;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjects (options: FindManyOptions<Project>): Promise<Project[]> {
|
async getProjects(options: FindManyOptions<Project>): Promise<Project[]> {
|
||||||
const projectRepository = this.dataSource.getRepository(Project);
|
const projectRepository = this.dataSource.getRepository(Project);
|
||||||
const projects = await projectRepository.find(options);
|
const projects = await projectRepository.find(options);
|
||||||
|
|
||||||
return projects;
|
return projects;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjectById (projectId: string): Promise<Project | null> {
|
async getProjectById(projectId: string): Promise<Project | null> {
|
||||||
const projectRepository = this.dataSource.getRepository(Project);
|
const projectRepository = this.dataSource.getRepository(Project);
|
||||||
|
|
||||||
const project = await projectRepository
|
const project = await projectRepository
|
||||||
@ -150,7 +150,20 @@ export class Database {
|
|||||||
return project;
|
return project;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjectsInOrganization (
|
async allProjectsWithoutDeployments(): Promise<Project[]> {
|
||||||
|
const projectRepository = this.dataSource.getRepository(Project);
|
||||||
|
|
||||||
|
const projects = await projectRepository
|
||||||
|
.createQueryBuilder('project')
|
||||||
|
.leftJoinAndSelect('project.deployments', 'deployment', 'deployment.deletedAt IS NULL') // Join only non-soft-deleted deployments
|
||||||
|
.where('deployment.id IS NULL') // Get projects where no deployments are present
|
||||||
|
.andWhere('project.auctionId IS NOT NULL') // Ensure auctionId is not null
|
||||||
|
.getMany();
|
||||||
|
|
||||||
|
return projects;
|
||||||
|
}
|
||||||
|
|
||||||
|
async getProjectsInOrganization(
|
||||||
userId: string,
|
userId: string,
|
||||||
organizationSlug: string
|
organizationSlug: string
|
||||||
): Promise<Project[]> {
|
): Promise<Project[]> {
|
||||||
@ -181,7 +194,7 @@ export class Database {
|
|||||||
/**
|
/**
|
||||||
* Get deployments with specified filter
|
* Get deployments with specified filter
|
||||||
*/
|
*/
|
||||||
async getDeployments (
|
async getDeployments(
|
||||||
options: FindManyOptions<Deployment>
|
options: FindManyOptions<Deployment>
|
||||||
): Promise<Deployment[]> {
|
): Promise<Deployment[]> {
|
||||||
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
||||||
@ -190,7 +203,7 @@ export class Database {
|
|||||||
return deployments;
|
return deployments;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDeploymentsByProjectId (projectId: string): Promise<Deployment[]> {
|
async getDeploymentsByProjectId(projectId: string): Promise<Deployment[]> {
|
||||||
return this.getDeployments({
|
return this.getDeployments({
|
||||||
relations: {
|
relations: {
|
||||||
project: true,
|
project: true,
|
||||||
@ -208,7 +221,7 @@ export class Database {
|
|||||||
});
|
});
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDeployment (
|
async getDeployment(
|
||||||
options: FindOneOptions<Deployment>
|
options: FindOneOptions<Deployment>
|
||||||
): Promise<Deployment | null> {
|
): Promise<Deployment | null> {
|
||||||
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
||||||
@ -217,14 +230,14 @@ export class Database {
|
|||||||
return deployment;
|
return deployment;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDomains (options: FindManyOptions<Domain>): Promise<Domain[]> {
|
async getDomains(options: FindManyOptions<Domain>): Promise<Domain[]> {
|
||||||
const domainRepository = this.dataSource.getRepository(Domain);
|
const domainRepository = this.dataSource.getRepository(Domain);
|
||||||
const domains = await domainRepository.find(options);
|
const domains = await domainRepository.find(options);
|
||||||
|
|
||||||
return domains;
|
return domains;
|
||||||
}
|
}
|
||||||
|
|
||||||
async addDeployment (data: DeepPartial<Deployment>): Promise<Deployment> {
|
async addDeployment(data: DeepPartial<Deployment>): Promise<Deployment> {
|
||||||
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
||||||
|
|
||||||
const id = nanoid();
|
const id = nanoid();
|
||||||
@ -238,7 +251,7 @@ export class Database {
|
|||||||
return deployment;
|
return deployment;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjectMembersByProjectId (
|
async getProjectMembersByProjectId(
|
||||||
projectId: string
|
projectId: string
|
||||||
): Promise<ProjectMember[]> {
|
): Promise<ProjectMember[]> {
|
||||||
const projectMemberRepository =
|
const projectMemberRepository =
|
||||||
@ -259,7 +272,7 @@ export class Database {
|
|||||||
return projectMembers;
|
return projectMembers;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getEnvironmentVariablesByProjectId (
|
async getEnvironmentVariablesByProjectId(
|
||||||
projectId: string,
|
projectId: string,
|
||||||
filter?: FindOptionsWhere<EnvironmentVariable>
|
filter?: FindOptionsWhere<EnvironmentVariable>
|
||||||
): Promise<EnvironmentVariable[]> {
|
): Promise<EnvironmentVariable[]> {
|
||||||
@ -278,7 +291,7 @@ export class Database {
|
|||||||
return environmentVariables;
|
return environmentVariables;
|
||||||
}
|
}
|
||||||
|
|
||||||
async removeProjectMemberById (projectMemberId: string): Promise<boolean> {
|
async removeProjectMemberById(projectMemberId: string): Promise<boolean> {
|
||||||
const projectMemberRepository =
|
const projectMemberRepository =
|
||||||
this.dataSource.getRepository(ProjectMember);
|
this.dataSource.getRepository(ProjectMember);
|
||||||
|
|
||||||
@ -293,7 +306,7 @@ export class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateProjectMemberById (
|
async updateProjectMemberById(
|
||||||
projectMemberId: string,
|
projectMemberId: string,
|
||||||
data: DeepPartial<ProjectMember>
|
data: DeepPartial<ProjectMember>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -307,7 +320,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async addProjectMember (
|
async addProjectMember(
|
||||||
data: DeepPartial<ProjectMember>
|
data: DeepPartial<ProjectMember>
|
||||||
): Promise<ProjectMember> {
|
): Promise<ProjectMember> {
|
||||||
const projectMemberRepository =
|
const projectMemberRepository =
|
||||||
@ -317,7 +330,7 @@ export class Database {
|
|||||||
return newProjectMember;
|
return newProjectMember;
|
||||||
}
|
}
|
||||||
|
|
||||||
async addEnvironmentVariables (
|
async addEnvironmentVariables(
|
||||||
data: DeepPartial<EnvironmentVariable>[]
|
data: DeepPartial<EnvironmentVariable>[]
|
||||||
): Promise<EnvironmentVariable[]> {
|
): Promise<EnvironmentVariable[]> {
|
||||||
const environmentVariableRepository =
|
const environmentVariableRepository =
|
||||||
@ -328,7 +341,7 @@ export class Database {
|
|||||||
return savedEnvironmentVariables;
|
return savedEnvironmentVariables;
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateEnvironmentVariable (
|
async updateEnvironmentVariable(
|
||||||
environmentVariableId: string,
|
environmentVariableId: string,
|
||||||
data: DeepPartial<EnvironmentVariable>
|
data: DeepPartial<EnvironmentVariable>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -342,7 +355,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async deleteEnvironmentVariable (
|
async deleteEnvironmentVariable(
|
||||||
environmentVariableId: string
|
environmentVariableId: string
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
const environmentVariableRepository =
|
const environmentVariableRepository =
|
||||||
@ -358,7 +371,7 @@ export class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjectMemberById (projectMemberId: string): Promise<ProjectMember> {
|
async getProjectMemberById(projectMemberId: string): Promise<ProjectMember> {
|
||||||
const projectMemberRepository =
|
const projectMemberRepository =
|
||||||
this.dataSource.getRepository(ProjectMember);
|
this.dataSource.getRepository(ProjectMember);
|
||||||
|
|
||||||
@ -381,7 +394,7 @@ export class Database {
|
|||||||
return projectMemberWithProject[0];
|
return projectMemberWithProject[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
async getProjectsBySearchText (
|
async getProjectsBySearchText(
|
||||||
userId: string,
|
userId: string,
|
||||||
searchText: string
|
searchText: string
|
||||||
): Promise<Project[]> {
|
): Promise<Project[]> {
|
||||||
@ -403,14 +416,14 @@ export class Database {
|
|||||||
return projects;
|
return projects;
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateDeploymentById (
|
async updateDeploymentById(
|
||||||
deploymentId: string,
|
deploymentId: string,
|
||||||
data: DeepPartial<Deployment>
|
data: DeepPartial<Deployment>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
return this.updateDeployment({ id: deploymentId }, data);
|
return this.updateDeployment({ id: deploymentId }, data);
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateDeployment (
|
async updateDeployment(
|
||||||
criteria: FindOptionsWhere<Deployment>,
|
criteria: FindOptionsWhere<Deployment>,
|
||||||
data: DeepPartial<Deployment>
|
data: DeepPartial<Deployment>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -420,7 +433,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateDeploymentsByProjectIds (
|
async updateDeploymentsByProjectIds(
|
||||||
projectIds: string[],
|
projectIds: string[],
|
||||||
data: DeepPartial<Deployment>
|
data: DeepPartial<Deployment>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -436,7 +449,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async deleteDeploymentById (deploymentId: string): Promise<boolean> {
|
async deleteDeploymentById(deploymentId: string): Promise<boolean> {
|
||||||
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
const deploymentRepository = this.dataSource.getRepository(Deployment);
|
||||||
const deployment = await deploymentRepository.findOneOrFail({
|
const deployment = await deploymentRepository.findOneOrFail({
|
||||||
where: {
|
where: {
|
||||||
@ -449,7 +462,7 @@ export class Database {
|
|||||||
return Boolean(deleteResult);
|
return Boolean(deleteResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
async addProject (user: User, organizationId: string, data: DeepPartial<Project>): Promise<Project> {
|
async addProject(user: User, organizationId: string, data: DeepPartial<Project>): Promise<Project> {
|
||||||
const projectRepository = this.dataSource.getRepository(Project);
|
const projectRepository = this.dataSource.getRepository(Project);
|
||||||
|
|
||||||
// TODO: Check if organization exists
|
// TODO: Check if organization exists
|
||||||
@ -468,7 +481,7 @@ export class Database {
|
|||||||
return projectRepository.save(newProject);
|
return projectRepository.save(newProject);
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateProjectById (
|
async updateProjectById(
|
||||||
projectId: string,
|
projectId: string,
|
||||||
data: DeepPartial<Project>
|
data: DeepPartial<Project>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -481,7 +494,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async deleteProjectById (projectId: string): Promise<boolean> {
|
async deleteProjectById(projectId: string): Promise<boolean> {
|
||||||
const projectRepository = this.dataSource.getRepository(Project);
|
const projectRepository = this.dataSource.getRepository(Project);
|
||||||
const project = await projectRepository.findOneOrFail({
|
const project = await projectRepository.findOneOrFail({
|
||||||
where: {
|
where: {
|
||||||
@ -497,7 +510,7 @@ export class Database {
|
|||||||
return Boolean(deleteResult);
|
return Boolean(deleteResult);
|
||||||
}
|
}
|
||||||
|
|
||||||
async deleteDomainById (domainId: string): Promise<boolean> {
|
async deleteDomainById(domainId: string): Promise<boolean> {
|
||||||
const domainRepository = this.dataSource.getRepository(Domain);
|
const domainRepository = this.dataSource.getRepository(Domain);
|
||||||
|
|
||||||
const deleteResult = await domainRepository.softDelete({ id: domainId });
|
const deleteResult = await domainRepository.softDelete({ id: domainId });
|
||||||
@ -509,21 +522,21 @@ export class Database {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
async addDomain (data: DeepPartial<Domain>): Promise<Domain> {
|
async addDomain(data: DeepPartial<Domain>): Promise<Domain> {
|
||||||
const domainRepository = this.dataSource.getRepository(Domain);
|
const domainRepository = this.dataSource.getRepository(Domain);
|
||||||
const newDomain = await domainRepository.save(data);
|
const newDomain = await domainRepository.save(data);
|
||||||
|
|
||||||
return newDomain;
|
return newDomain;
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDomain (options: FindOneOptions<Domain>): Promise<Domain | null> {
|
async getDomain(options: FindOneOptions<Domain>): Promise<Domain | null> {
|
||||||
const domainRepository = this.dataSource.getRepository(Domain);
|
const domainRepository = this.dataSource.getRepository(Domain);
|
||||||
const domain = await domainRepository.findOne(options);
|
const domain = await domainRepository.findOne(options);
|
||||||
|
|
||||||
return domain;
|
return domain;
|
||||||
}
|
}
|
||||||
|
|
||||||
async updateDomainById (
|
async updateDomainById(
|
||||||
domainId: string,
|
domainId: string,
|
||||||
data: DeepPartial<Domain>
|
data: DeepPartial<Domain>
|
||||||
): Promise<boolean> {
|
): Promise<boolean> {
|
||||||
@ -533,7 +546,7 @@ export class Database {
|
|||||||
return Boolean(updateResult.affected);
|
return Boolean(updateResult.affected);
|
||||||
}
|
}
|
||||||
|
|
||||||
async getDomainsByProjectId (
|
async getDomainsByProjectId(
|
||||||
projectId: string,
|
projectId: string,
|
||||||
filter?: FindOptionsWhere<Domain>
|
filter?: FindOptionsWhere<Domain>
|
||||||
): Promise<Domain[]> {
|
): Promise<Domain[]> {
|
||||||
|
@ -417,13 +417,7 @@ export class Registry {
|
|||||||
}
|
}
|
||||||
|
|
||||||
async getCompletedAuctionIds(auctionIds: string[]): Promise<string[]> {
|
async getCompletedAuctionIds(auctionIds: string[]): Promise<string[]> {
|
||||||
const validAuctionIds = auctionIds.filter((id): id is string => id !== '');
|
const auctions = await this.registry.getAuctionsByIds(auctionIds);
|
||||||
|
|
||||||
if (!validAuctionIds.length) {
|
|
||||||
return [];
|
|
||||||
}
|
|
||||||
|
|
||||||
const auctions = await this.registry.getAuctionsByIds(validAuctionIds);
|
|
||||||
|
|
||||||
const completedAuctions = auctions
|
const completedAuctions = auctions
|
||||||
.filter((auction: { id: string, status: string }) => auction.status === 'completed')
|
.filter((auction: { id: string, status: string }) => auction.status === 'completed')
|
||||||
|
@ -6,7 +6,7 @@ import { Permission } from './entity/ProjectMember';
|
|||||||
import { Domain } from './entity/Domain';
|
import { Domain } from './entity/Domain';
|
||||||
import { Project } from './entity/Project';
|
import { Project } from './entity/Project';
|
||||||
import { EnvironmentVariable } from './entity/EnvironmentVariable';
|
import { EnvironmentVariable } from './entity/EnvironmentVariable';
|
||||||
import { AddProjectFromTemplateInput, AuctionParams } from './types';
|
import { AddProjectFromTemplateInput, AuctionParams, EnvironmentVariables } from './types';
|
||||||
|
|
||||||
const log = debug('snowball:resolver');
|
const log = debug('snowball:resolver');
|
||||||
|
|
||||||
@ -218,7 +218,7 @@ export const createResolvers = async (service: Service): Promise<any> => {
|
|||||||
data: AddProjectFromTemplateInput;
|
data: AddProjectFromTemplateInput;
|
||||||
lrn: string;
|
lrn: string;
|
||||||
auctionParams: AuctionParams,
|
auctionParams: AuctionParams,
|
||||||
environmentVariables: { environments: string[]; key: string; value: string }[];
|
environmentVariables: EnvironmentVariables[];
|
||||||
},
|
},
|
||||||
context: any,
|
context: any,
|
||||||
) => {
|
) => {
|
||||||
@ -250,7 +250,7 @@ export const createResolvers = async (service: Service): Promise<any> => {
|
|||||||
data: DeepPartial<Project>;
|
data: DeepPartial<Project>;
|
||||||
lrn: string;
|
lrn: string;
|
||||||
auctionParams: AuctionParams,
|
auctionParams: AuctionParams,
|
||||||
environmentVariables: { environments: string[]; key: string; value: string }[];
|
environmentVariables: EnvironmentVariables[];
|
||||||
},
|
},
|
||||||
context: any,
|
context: any,
|
||||||
) => {
|
) => {
|
||||||
|
@ -20,6 +20,7 @@ import {
|
|||||||
AppDeploymentRecord,
|
AppDeploymentRecord,
|
||||||
AppDeploymentRemovalRecord,
|
AppDeploymentRemovalRecord,
|
||||||
AuctionParams,
|
AuctionParams,
|
||||||
|
EnvironmentVariables,
|
||||||
GitPushEventPayload,
|
GitPushEventPayload,
|
||||||
} from './types';
|
} from './types';
|
||||||
import { Role } from './entity/UserOrganization';
|
import { Role } from './entity/UserOrganization';
|
||||||
@ -167,7 +168,7 @@ export class Service {
|
|||||||
async updateDeploymentsWithRecordData(
|
async updateDeploymentsWithRecordData(
|
||||||
records: AppDeploymentRecord[],
|
records: AppDeploymentRecord[],
|
||||||
): Promise<void> {
|
): Promise<void> {
|
||||||
// get and update deployments to be updated using request id
|
// Fetch the deployments to be updated using deployment requestId
|
||||||
const deployments = await this.db.getDeployments({
|
const deployments = await this.db.getDeployments({
|
||||||
where: records.map((record) => ({
|
where: records.map((record) => ({
|
||||||
applicationDeploymentRequestId: record.attributes.request,
|
applicationDeploymentRequestId: record.attributes.request,
|
||||||
@ -220,10 +221,10 @@ export class Service {
|
|||||||
|
|
||||||
await Promise.all(deploymentUpdatePromises);
|
await Promise.all(deploymentUpdatePromises);
|
||||||
|
|
||||||
// if iscurrent is true for this deployment then update the old ones
|
// Get deployments that are in production environment
|
||||||
const prodDeployments = Object.values(recordToDeploymentsMap).filter(deployment => deployment.isCurrent);
|
const prodDeployments = Object.values(recordToDeploymentsMap).filter(deployment => deployment.isCurrent);
|
||||||
|
|
||||||
// Get deployment IDs of deployments that are in production environment
|
// Set the isCurrent state to false for the old deployments
|
||||||
for (const deployment of prodDeployments) {
|
for (const deployment of prodDeployments) {
|
||||||
const projectDeployments = await this.db.getDeploymentsByProjectId(deployment.projectId);
|
const projectDeployments = await this.db.getDeploymentsByProjectId(deployment.projectId);
|
||||||
const oldDeployments = projectDeployments
|
const oldDeployments = projectDeployments
|
||||||
@ -236,15 +237,6 @@ export class Service {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
// Get old deployments for ApplicationDeploymentRecords
|
|
||||||
// flter out deps with is current false
|
|
||||||
|
|
||||||
// loop over these deps
|
|
||||||
// get the project
|
|
||||||
// get all the deployemnts in that proj with the same deployer lrn (query filter not above updated dep)
|
|
||||||
// set is current to false
|
|
||||||
|
|
||||||
|
|
||||||
await Promise.all(deploymentUpdatePromises);
|
await Promise.all(deploymentUpdatePromises);
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -298,43 +290,30 @@ export class Service {
|
|||||||
* Calls the createDeploymentFromAuction method for deployments with completed auctions
|
* Calls the createDeploymentFromAuction method for deployments with completed auctions
|
||||||
*/
|
*/
|
||||||
async checkAuctionStatus(): Promise<void> {
|
async checkAuctionStatus(): Promise<void> {
|
||||||
const allProjects = await this.db.getProjects({
|
const projects = await this.db.allProjectsWithoutDeployments();
|
||||||
where: {
|
|
||||||
auctionId: Not(IsNull()),
|
|
||||||
},
|
|
||||||
relations: ['deployments'],
|
|
||||||
withDeleted: true,
|
|
||||||
});
|
|
||||||
|
|
||||||
// Should only check on the first deployment
|
const validAuctionIds = projects.map((project) => project.auctionId!)
|
||||||
const projects = allProjects.filter(project => {
|
.filter((id): id is string => Boolean(id));
|
||||||
if (project.deletedAt !== null) return false;
|
const completedAuctionIds = await this.laconicRegistry.getCompletedAuctionIds(validAuctionIds);
|
||||||
|
|
||||||
return project.deployments.length === 0;
|
const projectsToBedeployed = projects.filter((project) =>
|
||||||
});
|
completedAuctionIds.includes(project.auctionId!)
|
||||||
|
);
|
||||||
|
|
||||||
if (projects.length > 0) {
|
for (const project of projectsToBedeployed) {
|
||||||
const auctionIds = projects.map((project) => project.auctionId!);
|
const deployerLrns = await this.laconicRegistry.getAuctionWinningDeployers(project!.auctionId!);
|
||||||
const completedAuctionIds = await this.laconicRegistry.getCompletedAuctionIds(auctionIds);
|
|
||||||
const projectsToBedeployed = projects.filter((project) =>
|
|
||||||
completedAuctionIds.includes(project.auctionId!)
|
|
||||||
);
|
|
||||||
|
|
||||||
for (const project of projectsToBedeployed) {
|
if (!deployerLrns) {
|
||||||
const deployerLrns = await this.laconicRegistry.getAuctionWinningDeployers(project!.auctionId!);
|
log(`No winning deployer for auction ${project!.auctionId}`);
|
||||||
|
} else {
|
||||||
|
// Update project with deployer LRNs
|
||||||
|
await this.db.updateProjectById(project.id!, {
|
||||||
|
deployerLrns
|
||||||
|
});
|
||||||
|
|
||||||
if (!deployerLrns) {
|
for (const deployer of deployerLrns) {
|
||||||
log(`No winning deployer for auction ${project!.auctionId}`);
|
log(`Creating deployment for deployer LRN ${deployer}`);
|
||||||
} else {
|
await this.createDeploymentFromAuction(project, deployer);
|
||||||
// Update project with deployer LRNs
|
|
||||||
await this.db.updateProjectById(project.id!, {
|
|
||||||
deployerLrns
|
|
||||||
});
|
|
||||||
|
|
||||||
for (const deployer of deployerLrns) {
|
|
||||||
log(`Creating deployment for deployer LRN ${deployer}`);
|
|
||||||
await this.createDeploymentFromAuction(project, deployer);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -785,7 +764,7 @@ export class Service {
|
|||||||
data: AddProjectFromTemplateInput,
|
data: AddProjectFromTemplateInput,
|
||||||
lrn?: string,
|
lrn?: string,
|
||||||
auctionParams?: AuctionParams,
|
auctionParams?: AuctionParams,
|
||||||
environmentVariables?: { environments: string[]; key: string; value: string }[],
|
environmentVariables?: EnvironmentVariables[],
|
||||||
): Promise<Project | undefined> {
|
): Promise<Project | undefined> {
|
||||||
try {
|
try {
|
||||||
const octokit = await this.getOctokit(user.id);
|
const octokit = await this.getOctokit(user.id);
|
||||||
@ -835,7 +814,7 @@ export class Service {
|
|||||||
data: DeepPartial<Project>,
|
data: DeepPartial<Project>,
|
||||||
lrn?: string,
|
lrn?: string,
|
||||||
auctionParams?: AuctionParams,
|
auctionParams?: AuctionParams,
|
||||||
environmentVariables?: { environments: string[]; key: string; value: string }[],
|
environmentVariables?: EnvironmentVariables[],
|
||||||
): Promise<Project | undefined> {
|
): Promise<Project | undefined> {
|
||||||
const organization = await this.db.getOrganization({
|
const organization = await this.db.getOrganization({
|
||||||
where: {
|
where: {
|
||||||
@ -846,9 +825,9 @@ export class Service {
|
|||||||
throw new Error('Organization does not exist');
|
throw new Error('Organization does not exist');
|
||||||
}
|
}
|
||||||
|
|
||||||
const project = await this.db.addProject(user, organization.id, data);4
|
const project = await this.db.addProject(user, organization.id, data);
|
||||||
|
|
||||||
if(environmentVariables) {
|
if (environmentVariables) {
|
||||||
await this.addEnvironmentVariables(project.id, environmentVariables);
|
await this.addEnvironmentVariables(project.id, environmentVariables);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -76,3 +76,9 @@ export interface AuctionParams {
|
|||||||
maxPrice: string,
|
maxPrice: string,
|
||||||
numProviders: number,
|
numProviders: number,
|
||||||
}
|
}
|
||||||
|
|
||||||
|
export interface EnvironmentVariables {
|
||||||
|
environments: string[],
|
||||||
|
key: string,
|
||||||
|
value: string,
|
||||||
|
}
|
||||||
|
@ -1,6 +1,6 @@
|
|||||||
import { useCallback, useState } from 'react';
|
import { useCallback, useState } from 'react';
|
||||||
import { useForm, Controller } from 'react-hook-form';
|
import { useForm, Controller } from 'react-hook-form';
|
||||||
import { FormProvider, FieldValues } from 'react-hook-form';
|
import { FormProvider, FieldValues } from 'react-hook-form';
|
||||||
import { useNavigate, useSearchParams } from 'react-router-dom';
|
import { useNavigate, useSearchParams } from 'react-router-dom';
|
||||||
import { useMediaQuery } from 'usehooks-ts';
|
import { useMediaQuery } from 'usehooks-ts';
|
||||||
import { AddEnvironmentVariableInput, AuctionParams } from 'gql-client';
|
import { AddEnvironmentVariableInput, AuctionParams } from 'gql-client';
|
||||||
@ -59,18 +59,18 @@ const Configure = () => {
|
|||||||
setIsLoading(true);
|
setIsLoading(true);
|
||||||
let projectId: string | null = null;
|
let projectId: string | null = null;
|
||||||
|
|
||||||
try {
|
try {
|
||||||
let lrn: string | undefined;
|
let lrn: string | undefined;
|
||||||
let auctionParams: AuctionParams | undefined;
|
let auctionParams: AuctionParams | undefined;
|
||||||
|
|
||||||
if (data.option === 'LRN') {
|
if (data.option === 'LRN') {
|
||||||
lrn = data.lrn;
|
lrn = data.lrn;
|
||||||
} else if (data.option === 'Auction') {
|
} else if (data.option === 'Auction') {
|
||||||
auctionParams = {
|
auctionParams = {
|
||||||
numProviders: Number(data.numProviders!),
|
numProviders: Number(data.numProviders!),
|
||||||
maxPrice: (data.maxPrice!).toString(),
|
maxPrice: (data.maxPrice!).toString(),
|
||||||
};
|
};
|
||||||
}
|
}
|
||||||
|
|
||||||
if (templateId) {
|
if (templateId) {
|
||||||
const projectData: any = {
|
const projectData: any = {
|
||||||
@ -125,7 +125,7 @@ const Configure = () => {
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
const createEnvironmentVariablesHandler = useCallback(
|
const handleFormSubmit = useCallback(
|
||||||
async (createFormData: FieldValues) => {
|
async (createFormData: FieldValues) => {
|
||||||
const environmentVariables = createFormData.variables.map((variable: any) => {
|
const environmentVariables = createFormData.variables.map((variable: any) => {
|
||||||
return {
|
return {
|
||||||
@ -165,20 +165,20 @@ const Configure = () => {
|
|||||||
}
|
}
|
||||||
if (templateId) {
|
if (templateId) {
|
||||||
createFormData.option === 'Auction'
|
createFormData.option === 'Auction'
|
||||||
? navigate(
|
? navigate(
|
||||||
`/${orgSlug}/projects/create/success/${projectId}?isAuction=true`,
|
`/${orgSlug}/projects/create/success/${projectId}?isAuction=true`,
|
||||||
)
|
)
|
||||||
: navigate(
|
: navigate(
|
||||||
`/${orgSlug}/projects/create/template/deploy?projectId=${projectId}&templateId=${templateId}`
|
`/${orgSlug}/projects/create/template/deploy?projectId=${projectId}&templateId=${templateId}`
|
||||||
);
|
);
|
||||||
} else {
|
} else {
|
||||||
createFormData.option === 'Auction'
|
createFormData.option === 'Auction'
|
||||||
? navigate(
|
? navigate(
|
||||||
`/${orgSlug}/projects/create/success/${projectId}?isAuction=true`
|
`/${orgSlug}/projects/create/success/${projectId}?isAuction=true`
|
||||||
)
|
)
|
||||||
: navigate(
|
: navigate(
|
||||||
`/${orgSlug}/projects/create/deploy?projectId=${projectId}`
|
`/${orgSlug}/projects/create/deploy?projectId=${projectId}`
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
},
|
},
|
||||||
[client, createProject, dismiss, toast]
|
[client, createProject, dismiss, toast]
|
||||||
@ -201,7 +201,7 @@ const Configure = () => {
|
|||||||
|
|
||||||
<div className="flex flex-col gap-6 lg:gap-8 w-full">
|
<div className="flex flex-col gap-6 lg:gap-8 w-full">
|
||||||
<FormProvider {...methods}>
|
<FormProvider {...methods}>
|
||||||
<form onSubmit={methods.handleSubmit(createEnvironmentVariablesHandler)}>
|
<form onSubmit={methods.handleSubmit(handleFormSubmit)}>
|
||||||
<div className="flex flex-col justify-start gap-4 mb-6">
|
<div className="flex flex-col justify-start gap-4 mb-6">
|
||||||
<Controller
|
<Controller
|
||||||
name="option"
|
name="option"
|
||||||
@ -236,7 +236,7 @@ const Configure = () => {
|
|||||||
<Controller
|
<Controller
|
||||||
name="lrn"
|
name="lrn"
|
||||||
control={methods.control}
|
control={methods.control}
|
||||||
rules={{ required : true }}
|
rules={{ required: true }}
|
||||||
render={({ field: { value, onChange } }) => (
|
render={({ field: { value, onChange } }) => (
|
||||||
<Input value={value} onChange={onChange} />
|
<Input value={value} onChange={onChange} />
|
||||||
)}
|
)}
|
||||||
@ -256,7 +256,7 @@ const Configure = () => {
|
|||||||
<Controller
|
<Controller
|
||||||
name="numProviders"
|
name="numProviders"
|
||||||
control={methods.control}
|
control={methods.control}
|
||||||
rules={{ required : true }}
|
rules={{ required: true }}
|
||||||
render={({ field: { value, onChange } }) => (
|
render={({ field: { value, onChange } }) => (
|
||||||
<Input type="number" value={value} onChange={onChange} />
|
<Input type="number" value={value} onChange={onChange} />
|
||||||
)}
|
)}
|
||||||
@ -269,7 +269,7 @@ const Configure = () => {
|
|||||||
<Controller
|
<Controller
|
||||||
name="maxPrice"
|
name="maxPrice"
|
||||||
control={methods.control}
|
control={methods.control}
|
||||||
rules={{ required : true }}
|
rules={{ required: true }}
|
||||||
render={({ field: { value, onChange } }) => (
|
render={({ field: { value, onChange } }) => (
|
||||||
<Input type="number" value={value} onChange={onChange} />
|
<Input type="number" value={value} onChange={onChange} />
|
||||||
)}
|
)}
|
||||||
|
@ -8,7 +8,6 @@ import { useGQLClient } from 'context/GQLClientContext';
|
|||||||
import { EnvironmentVariablesFormValues } from '../../../../../types';
|
import { EnvironmentVariablesFormValues } from '../../../../../types';
|
||||||
import HorizontalLine from 'components/HorizontalLine';
|
import HorizontalLine from 'components/HorizontalLine';
|
||||||
import { Heading } from 'components/shared/Heading';
|
import { Heading } from 'components/shared/Heading';
|
||||||
// import { Checkbox } from 'components/shared/Checkbox';
|
|
||||||
import { PlusIcon } from 'components/shared/CustomIcon';
|
import { PlusIcon } from 'components/shared/CustomIcon';
|
||||||
import { ProjectSettingContainer } from 'components/projects/project/settings/ProjectSettingContainer';
|
import { ProjectSettingContainer } from 'components/projects/project/settings/ProjectSettingContainer';
|
||||||
import { useToast } from 'components/shared/Toast';
|
import { useToast } from 'components/shared/Toast';
|
||||||
@ -79,7 +78,7 @@ export const EnvironmentVariablesTabPanel = () => {
|
|||||||
await client.addEnvironmentVariables(id!, environmentVariables);
|
await client.addEnvironmentVariables(id!, environmentVariables);
|
||||||
|
|
||||||
if (isEnvironmentVariablesAdded) {
|
if (isEnvironmentVariablesAdded) {
|
||||||
// reset();
|
methods.reset();
|
||||||
setCreateNewVariable((cur) => !cur);
|
setCreateNewVariable((cur) => !cur);
|
||||||
|
|
||||||
fetchEnvironmentVariables(id);
|
fetchEnvironmentVariables(id);
|
||||||
|
@ -1,6 +1,7 @@
|
|||||||
import { useEffect, useMemo } from 'react';
|
import { useEffect, useMemo } from 'react';
|
||||||
import { useFieldArray, useFormContext } from 'react-hook-form';
|
import { useFieldArray, useFormContext } from 'react-hook-form';
|
||||||
|
|
||||||
|
// TODO: Use custom checkbox component
|
||||||
import { Checkbox } from '@snowballtools/material-tailwind-react-fork';
|
import { Checkbox } from '@snowballtools/material-tailwind-react-fork';
|
||||||
|
|
||||||
import { Button } from 'components/shared/Button';
|
import { Button } from 'components/shared/Button';
|
||||||
|
Loading…
Reference in New Issue
Block a user