Skip to content

Commit 7f4eb63

Browse files
committed
Merge branch 'main' into config-cache
2 parents 7dbbe56 + 9ab0813 commit 7f4eb63

File tree

17 files changed

+185
-237
lines changed

17 files changed

+185
-237
lines changed

install.ts

Lines changed: 0 additions & 56 deletions
This file was deleted.

src/cmd/lib/checkout.ts

Lines changed: 3 additions & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -44,7 +44,7 @@ export const checkoutCmd = new Command()
4444
) => {
4545
doWithSpinner("Checking out branch...", async (spinner) => {
4646
const vt = VTClient.from(await findVtRoot(Deno.cwd()));
47-
const state = await vt.getMeta().loadState();
47+
const config = await vt.getMeta().loadState();
4848

4949
const statusResult = await vt.status();
5050

@@ -55,7 +55,7 @@ export const checkoutCmd = new Command()
5555
await vt.isDirty({
5656
statusResult: await vt.status({
5757
branchId: (await branchIdToBranch(
58-
state.project.id,
58+
config.project.id,
5959
existingBranchName,
6060
)).id,
6161
}),
@@ -71,7 +71,7 @@ export const checkoutCmd = new Command()
7171
try {
7272
checkoutResult = await vt
7373
.checkout(branch, {
74-
forkedFrom: state.branch.id,
74+
forkedFrom: config.branch.id,
7575
statusResult,
7676
});
7777

src/cmd/lib/create.ts

Lines changed: 4 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -1,7 +1,5 @@
11
import { Command } from "@cliffy/command";
22
import { basename, join } from "@std/path";
3-
import { checkDirectory } from "~/utils.ts";
4-
import { DEFAULT_IGNORE_PATTERNS } from "~/consts.ts";
53
import VTClient from "~/vt/vt/VTClient.ts";
64
import { user } from "~/sdk.ts";
75
import { APIError } from "@valtown/sdk";
@@ -57,7 +55,10 @@ vt checkout main`,
5755
targetDir?: string,
5856
) => {
5957
doWithSpinner("Creating project...", async (spinner) => {
60-
let rootPath = targetDir || Deno.cwd();
58+
let rootPath: string;
59+
if (!targetDir) {
60+
rootPath = join(Deno.cwd(), projectName);
61+
} else rootPath = targetDir;
6162

6263
// Check for mutually exclusive privacy flags
6364
const privacyFlags =
@@ -81,14 +82,6 @@ vt checkout main`,
8182
);
8283
await vt.addEditorFiles();
8384

84-
// If no target directory specified, use project name
85-
if (targetDir === undefined) rootPath = join(rootPath, projectName);
86-
87-
// Make sure directory is safe to create project in
88-
await checkDirectory(rootPath, {
89-
gitignoreRules: DEFAULT_IGNORE_PATTERNS,
90-
});
91-
9285
spinner.succeed(
9386
`Created ${privacy} project ${projectName} in ./${
9487
basename(rootPath)

src/consts.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -50,10 +50,12 @@ export const ProjectItems = [
5050
"directory",
5151
] as const;
5252

53+
export const JSON_INDENT_SPACES = 4;
54+
5355
export const VAL_TOWN_PROJECT_URL_REGEX =
5456
/^http[s]?:\/\/www\.val\.town\/x\/([^\/]+)\/([^\/]+)$/;
5557

5658
export type ProjectItemType = typeof ProjectItems[number];
5759
export type ProjectFileType = Exclude<ProjectItemType, "directory">;
5860

59-
export const JSON_INDENT_SPACES = 4;
61+
export const RECENT_VERSION_COUNT = 5;

src/sdk.ts

Lines changed: 18 additions & 12 deletions
Original file line numberDiff line numberDiff line change
@@ -64,43 +64,49 @@ async function filePathToFile(
6464
* @param {string} projectId The ID of the project
6565
* @param {Object} params The parameters for listing project items
6666
* @param {string} params.path The root path to start listing from
67-
* @param {string} params.branch_id The ID of the project branch to reference
68-
* @param {number} params.version The version of the project
67+
* @param {string} [params.branch_id] The ID of the project branch to reference. Defaults to main.
68+
* @param {number} [params.version] - The version of the project. Defaults to latest.
6969
* @param {Object} [params.options] Additional options for filtering
7070
* @param {boolean} [params.options.recursive=true] Whether to recursively list files in subdirectories
7171
* @returns {Promise<Set<string>>} Promise resolving to a Set of file paths
7272
* @throws {Error} if the API request fails
7373
*/
7474
export async function listProjectItems(
7575
projectId: string,
76-
{ path, branch_id, version, recursive }: {
76+
{
77+
path,
78+
branch_id,
79+
version,
80+
recursive,
81+
}: {
7782
path: string;
78-
branch_id: string;
79-
version: number;
83+
branch_id?: string;
84+
version?: number;
8085
recursive?: boolean;
8186
},
8287
): Promise<ValTown.Projects.FileRetrieveResponse.Data[]> {
8388
const files: ValTown.Projects.FileRetrieveResponse.Data[] = [];
8489
let cursor = 0;
85-
const batch = 100;
90+
const batchSize = 100; // Single, reasonable batch size
8691

8792
while (true) {
8893
const resp = await sdk.projects.files.retrieve(projectId, {
8994
path,
9095
offset: cursor,
91-
limit: batch,
96+
limit: batchSize,
9297
branch_id,
9398
version,
94-
recursive: recursive ?? true,
99+
recursive,
95100
});
96101

97-
resp.data.forEach((file) => files.push(file));
102+
// Add the files to our result array
103+
files.push(...resp.data);
98104

99-
// If no more results or we've reached the end, break
100-
if (resp.data.length === 0) break;
105+
// If we got fewer items than the batch size, we've reached the end
106+
if (!resp.links.next) break;
101107

102108
// Move to next batch
103-
cursor += batch;
109+
cursor += batchSize;
104110
}
105111

106112
return files;

src/vt/lib/checkout.ts

Lines changed: 3 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -113,6 +113,7 @@ export function checkout(
113113
path: "",
114114
branch_id: fromBranch.id,
115115
version: fromBranch.version,
116+
recursive: true,
116117
}).then((resp) => resp.map((file) => file.path)),
117118
);
118119

@@ -122,6 +123,7 @@ export function checkout(
122123
path: "",
123124
branch_id: checkoutBranchId,
124125
version: checkoutVersion,
126+
recursive: true,
125127
}).then((resp) => resp.map((file) => file.path)),
126128
);
127129

@@ -141,7 +143,7 @@ export function checkout(
141143
const relativePath = relative(args.targetDir, entry.path);
142144

143145
// Skip files that match gitignore rules
144-
if (await shouldIgnore(relativePath, args.gitignoreRules)) continue;
146+
if (shouldIgnore(relativePath, args.gitignoreRules)) continue;
145147

146148
// Skip root directory
147149
if (relativePath === "" || entry.path === args.targetDir) continue;

src/vt/lib/clone.ts

Lines changed: 22 additions & 21 deletions
Original file line numberDiff line numberDiff line change
@@ -35,29 +35,30 @@ export function clone({
3535
version,
3636
branch_id: branchId,
3737
path: "",
38+
recursive: true,
3839
});
3940

40-
await Promise.all(projectItems
41-
.map(async (file) => {
42-
// Skip ignored files
43-
if (shouldIgnore(file.path, gitignoreRules)) return;
44-
45-
if (file.type === "directory") {
46-
// Create directories, even if they would otherwise get created during
47-
// the createFile call later, so that we get empty directories
48-
await ensureDir(path.join(tmpDir, file.path));
49-
} else {
50-
// Start a create file task in the background
51-
const fullPath = path.join(tmpDir, file.path);
52-
await createFile(
53-
fullPath,
54-
projectId,
55-
branchId,
56-
version,
57-
file,
58-
);
59-
}
60-
}));
41+
await Promise.all(
42+
projectItems
43+
.filter((file) => !shouldIgnore(file.path, gitignoreRules))
44+
.map(async (file) => {
45+
if (file.type === "directory") {
46+
// Create directories, even if they would otherwise get created during
47+
// the createFile call later, so that we get empty directories
48+
await ensureDir(path.join(tmpDir, file.path));
49+
} else {
50+
// Start a create file task in the background
51+
const fullPath = path.join(tmpDir, file.path);
52+
await createFile(
53+
fullPath,
54+
projectId,
55+
branchId,
56+
version,
57+
file,
58+
);
59+
}
60+
}),
61+
);
6162
},
6263
targetDir,
6364
"vt_clone_",

src/vt/lib/paths.ts

Lines changed: 35 additions & 32 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,8 @@
1-
import { DEFAULT_VAL_TYPE, type ProjectItemType } from "~/consts.ts";
1+
import {
2+
DEFAULT_VAL_TYPE,
3+
RECENT_VERSION_COUNT,
4+
type ProjectItemType
5+
} from "~/consts.ts";
26
import { filePathToFile } from "~/sdk.ts";
37
import { compile as compileGitignore } from "gitignore-parser";
48

@@ -27,42 +31,41 @@ async function getProjectItemType(
2731
version: number,
2832
filePath: string,
2933
): Promise<ProjectItemType> {
30-
try {
31-
// If a file already exists in the project at the given path, then the type
32-
// is whatever it already is on the website.
33-
return await filePathToFile(projectId, branchId, version, filePath)
34-
.then((resp) => resp.type);
35-
} catch (e) {
36-
// Otherwise, if it ends in .ts, .js, .tsx, or .jsx, it is a val
37-
if (e instanceof Deno.errors.NotFound) {
38-
if (/\.(ts|tsx|js|jsx)$/.test(filePath)) {
39-
const isCron = filePath.includes("cron");
40-
const isHttp = filePath.includes("http");
41-
const isEmail = filePath.includes("email");
34+
for (let i = version; i > version - RECENT_VERSION_COUNT; i--) {
35+
try {
36+
return await filePathToFile(projectId, branchId, version, filePath)
37+
.then((resp) => resp.type);
38+
} catch (e) {
39+
if (e instanceof Deno.errors.NotFound) {
40+
continue;
41+
} else throw e;
42+
}
43+
}
4244

43-
// If it's ambiguous then it is a script val by default
44-
if ([isCron, isHttp, isEmail].filter(Boolean).length > 1) {
45-
return DEFAULT_VAL_TYPE;
46-
}
45+
// Otherwise, if it ends in .ts, .js, .tsx, or .jsx, it is a val
46+
if (/\.(ts|tsx|js|jsx)$/.test(filePath)) {
47+
const isCron = filePath.includes("cron");
48+
const isHttp = filePath.includes("http");
49+
const isEmail = filePath.includes("email");
4750

48-
// But otherwise look at the file name and try to figure out what type
49-
// of val it is based on whether the file name contains a pattern like
50-
// "cron," etc
51-
if (isCron) return "interval";
52-
if (isHttp) return "http";
53-
if (isEmail) return "email";
51+
// If it's ambiguous then it is a script val by default
52+
if ([isCron, isHttp, isEmail].filter(Boolean).length > 1) {
53+
return DEFAULT_VAL_TYPE;
54+
}
5455

55-
// If we can't figure it out, default to script
56-
return DEFAULT_VAL_TYPE;
57-
}
56+
// But otherwise look at the file name and try to figure out what type
57+
// of val it is based on whether the file name contains a pattern like
58+
// "cron," etc
59+
if (isCron) return "interval";
60+
if (isHttp) return "http";
61+
if (isEmail) return "email";
5862

59-
// Otherwise, it's just a plain old file val
60-
return "file";
61-
} else {
62-
// Re-throw any other errors
63-
throw e;
64-
}
63+
// If we can't figure it out, default to script
64+
return DEFAULT_VAL_TYPE;
6565
}
66+
67+
// Otherwise, it's just a plain old file val
68+
return "file";
6669
}
6770

6871
/**

src/vt/lib/pull.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -64,6 +64,7 @@ export function pull({
6464
path: "",
6565
branch_id: branchId,
6666
version,
67+
recursive: true,
6768
}).then((resp) => resp.map((file) => file.path)),
6869
);
6970

0 commit comments

Comments
 (0)