Use query builder to get projects without deployments
All checks were successful
Lint / lint (20.x) (pull_request) Successful in 4m13s

This commit is contained in:
IshaVenikar 2024-10-21 10:07:34 +05:30
parent 1bd28e0309
commit 83819fc211
8 changed files with 120 additions and 128 deletions

View File

@ -150,6 +150,19 @@ export class Database {
return project;
}
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,
organizationSlug: string

View File

@ -417,13 +417,7 @@ export class Registry {
}
async getCompletedAuctionIds(auctionIds: string[]): Promise<string[]> {
const validAuctionIds = auctionIds.filter((id): id is string => id !== '');
if (!validAuctionIds.length) {
return [];
}
const auctions = await this.registry.getAuctionsByIds(validAuctionIds);
const auctions = await this.registry.getAuctionsByIds(auctionIds);
const completedAuctions = auctions
.filter((auction: { id: string, status: string }) => auction.status === 'completed')

View File

@ -6,7 +6,7 @@ import { Permission } from './entity/ProjectMember';
import { Domain } from './entity/Domain';
import { Project } from './entity/Project';
import { EnvironmentVariable } from './entity/EnvironmentVariable';
import { AddProjectFromTemplateInput, AuctionParams } from './types';
import { AddProjectFromTemplateInput, AuctionParams, EnvironmentVariables } from './types';
const log = debug('snowball:resolver');
@ -218,7 +218,7 @@ export const createResolvers = async (service: Service): Promise<any> => {
data: AddProjectFromTemplateInput;
lrn: string;
auctionParams: AuctionParams,
environmentVariables: { environments: string[]; key: string; value: string }[];
environmentVariables: EnvironmentVariables[];
},
context: any,
) => {
@ -250,7 +250,7 @@ export const createResolvers = async (service: Service): Promise<any> => {
data: DeepPartial<Project>;
lrn: string;
auctionParams: AuctionParams,
environmentVariables: { environments: string[]; key: string; value: string }[];
environmentVariables: EnvironmentVariables[];
},
context: any,
) => {

View File

@ -20,6 +20,7 @@ import {
AppDeploymentRecord,
AppDeploymentRemovalRecord,
AuctionParams,
EnvironmentVariables,
GitPushEventPayload,
} from './types';
import { Role } from './entity/UserOrganization';
@ -167,7 +168,7 @@ export class Service {
async updateDeploymentsWithRecordData(
records: AppDeploymentRecord[],
): 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({
where: records.map((record) => ({
applicationDeploymentRequestId: record.attributes.request,
@ -220,10 +221,10 @@ export class Service {
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);
// 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) {
const projectDeployments = await this.db.getDeploymentsByProjectId(deployment.projectId);
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);
}
@ -298,24 +290,12 @@ export class Service {
* Calls the createDeploymentFromAuction method for deployments with completed auctions
*/
async checkAuctionStatus(): Promise<void> {
const allProjects = await this.db.getProjects({
where: {
auctionId: Not(IsNull()),
},
relations: ['deployments'],
withDeleted: true,
});
const projects = await this.db.allProjectsWithoutDeployments();
// Should only check on the first deployment
const projects = allProjects.filter(project => {
if (project.deletedAt !== null) return false;
const validAuctionIds = projects.map((project) => project.auctionId!)
.filter((id): id is string => Boolean(id));
const completedAuctionIds = await this.laconicRegistry.getCompletedAuctionIds(validAuctionIds);
return project.deployments.length === 0;
});
if (projects.length > 0) {
const auctionIds = projects.map((project) => project.auctionId!);
const completedAuctionIds = await this.laconicRegistry.getCompletedAuctionIds(auctionIds);
const projectsToBedeployed = projects.filter((project) =>
completedAuctionIds.includes(project.auctionId!)
);
@ -337,7 +317,6 @@ export class Service {
}
}
}
}
this.auctionStatusCheckTimeout = setTimeout(() => {
this.checkAuctionStatus();
@ -785,7 +764,7 @@ export class Service {
data: AddProjectFromTemplateInput,
lrn?: string,
auctionParams?: AuctionParams,
environmentVariables?: { environments: string[]; key: string; value: string }[],
environmentVariables?: EnvironmentVariables[],
): Promise<Project | undefined> {
try {
const octokit = await this.getOctokit(user.id);
@ -835,7 +814,7 @@ export class Service {
data: DeepPartial<Project>,
lrn?: string,
auctionParams?: AuctionParams,
environmentVariables?: { environments: string[]; key: string; value: string }[],
environmentVariables?: EnvironmentVariables[],
): Promise<Project | undefined> {
const organization = await this.db.getOrganization({
where: {
@ -846,7 +825,7 @@ export class Service {
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) {
await this.addEnvironmentVariables(project.id, environmentVariables);

View File

@ -76,3 +76,9 @@ export interface AuctionParams {
maxPrice: string,
numProviders: number,
}
export interface EnvironmentVariables {
environments: string[],
key: string,
value: string,
}

View File

@ -125,7 +125,7 @@ const Configure = () => {
}
};
const createEnvironmentVariablesHandler = useCallback(
const handleFormSubmit = useCallback(
async (createFormData: FieldValues) => {
const environmentVariables = createFormData.variables.map((variable: any) => {
return {
@ -201,7 +201,7 @@ const Configure = () => {
<div className="flex flex-col gap-6 lg:gap-8 w-full">
<FormProvider {...methods}>
<form onSubmit={methods.handleSubmit(createEnvironmentVariablesHandler)}>
<form onSubmit={methods.handleSubmit(handleFormSubmit)}>
<div className="flex flex-col justify-start gap-4 mb-6">
<Controller
name="option"

View File

@ -8,7 +8,6 @@ import { useGQLClient } from 'context/GQLClientContext';
import { EnvironmentVariablesFormValues } from '../../../../../types';
import HorizontalLine from 'components/HorizontalLine';
import { Heading } from 'components/shared/Heading';
// import { Checkbox } from 'components/shared/Checkbox';
import { PlusIcon } from 'components/shared/CustomIcon';
import { ProjectSettingContainer } from 'components/projects/project/settings/ProjectSettingContainer';
import { useToast } from 'components/shared/Toast';
@ -79,7 +78,7 @@ export const EnvironmentVariablesTabPanel = () => {
await client.addEnvironmentVariables(id!, environmentVariables);
if (isEnvironmentVariablesAdded) {
// reset();
methods.reset();
setCreateNewVariable((cur) => !cur);
fetchEnvironmentVariables(id);

View File

@ -1,6 +1,7 @@
import { useEffect, useMemo } from 'react';
import { useFieldArray, useFormContext } from 'react-hook-form';
// TODO: Use custom checkbox component
import { Checkbox } from '@snowballtools/material-tailwind-react-fork';
import { Button } from 'components/shared/Button';