Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
4 changes: 0 additions & 4 deletions build/conda-nonconda-test-requirements.txt

This file was deleted.

1 change: 0 additions & 1 deletion build/venv-smoke-test-requirements.txt

This file was deleted.

11 changes: 0 additions & 11 deletions build/venv-test-ipywidgets7-requirements.txt

This file was deleted.

16 changes: 15 additions & 1 deletion build/venv-test-ipywidgets8-requirements.txt
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# List of requirements for ipython tests
numpy
numpy>=1.22.2
pandas
# Install jupyter itself so we end up with a kernel
jupyter
Expand All @@ -8,3 +8,17 @@ ipywidgets
anywidget
matplotlib
ipympl

# Security updates for transitive dependencies
pillow>=10.2.0
setuptools>=78.1.1
zipp>=3.19.1
tornado>=6.4.1
anyio>=4.4.0
requests>=2.32.4
fonttools>=4.43.0
jupyter-server>=2.14.1
jupyter-core>=5.8.0
ipython>=8.10.0
urllib3>=2.2.2
jupyterlab>=4.4.8
1,040 changes: 540 additions & 500 deletions package-lock.json

Large diffs are not rendered by default.

4 changes: 2 additions & 2 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -2196,7 +2196,7 @@
"fast-deep-equal": "^2.0.1",
"format-util": "^1.0.5",
"fs-extra": "^4.0.3",
"glob": "^7.1.2",
"glob": "^9.3.5",
"iconv-lite": "^0.6.3",
"immer": "^10.1.3",
"inversify": "^6.0.1",
Expand Down Expand Up @@ -2230,7 +2230,6 @@
"slickgrid": "^2.4.17",
"stack-trace": "0.0.10",
"strip-comments": "^2.0.1",
"styled-components": "^5.2.1",
"svg-to-pdfkit": "^0.1.8",
"tailwind-merge": "^3.3.1",
"tcp-port-used": "^1.0.1",
Expand Down Expand Up @@ -2309,6 +2308,7 @@
"@vscode/zeromq": "^0.2.3",
"acorn": "^8.9.0",
"autoprefixer": "^10.4.21",
"bare-events": "^2.8.1",
"buffer": "^6.0.3",
"bufferutil": "^4.0.6",
"chai": "^4.3.10",
Expand Down
9 changes: 3 additions & 6 deletions src/platform/common/platform/fileSystem.node.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,10 +3,9 @@

import * as path from '../../../platform/vscode-path/path';
import * as fs from 'fs-extra';
import glob from 'glob';
import { glob } from 'glob';
import { injectable } from 'inversify';
import * as tmp from 'tmp';
import { promisify } from 'util';
import { TemporaryFile } from './types';
import { IFileSystemNode } from './types.node';
import { ENCODING, FileSystem as FileSystemBase } from './fileSystem';
Expand All @@ -19,10 +18,8 @@ import { getFilePath } from './fs-paths';
*/
@injectable()
export class FileSystem extends FileSystemBase implements IFileSystemNode {
private globFiles: (pat: string, options?: { cwd: string; dot?: boolean }) => Promise<string[]>;
constructor() {
super();
this.globFiles = promisify(glob);
private async globFiles(pat: string, options?: { cwd: string; dot?: boolean }): Promise<string[]> {
return glob(pat, options || {});
}

public createLocalWriteStream(path: string): fs.WriteStream {
Expand Down
92 changes: 92 additions & 0 deletions src/platform/common/platform/fileSystem.node.unit.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

import { assert } from 'chai';
import * as fs from 'fs-extra';
import * as path from '../../../platform/vscode-path/path';
import * as os from 'os';
import { FileSystem } from './fileSystem.node';

suite('FileSystem - glob functionality', () => {
let fileSystem: FileSystem;
let tempDir: string;

setup(async () => {
fileSystem = new FileSystem();
tempDir = await fs.mkdtemp(path.join(os.tmpdir(), 'vscode-deepnote-test-'));
});

teardown(async () => {
await fs.remove(tempDir);
});

test('searchLocal should find files matching pattern', async () => {
// Create test files
await fs.writeFile(path.join(tempDir, 'test1.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'test2.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'test.js'), 'content');

const results = await fileSystem.searchLocal('*.ts', tempDir);

assert.strictEqual(results.length, 2);
assert.ok(results.some((f) => f.endsWith('test1.ts')));
assert.ok(results.some((f) => f.endsWith('test2.ts')));
});

test('searchLocal should find files in subdirectories with ** pattern', async () => {
// Create test files in subdirectories
await fs.ensureDir(path.join(tempDir, 'sub1'));
await fs.ensureDir(path.join(tempDir, 'sub2'));
await fs.writeFile(path.join(tempDir, 'sub1', 'test1.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'sub2', 'test2.ts'), 'content');

const results = await fileSystem.searchLocal('**/*.ts', tempDir);

assert.strictEqual(results.length, 2);
assert.ok(results.some((f) => f.includes('sub1') && f.endsWith('test1.ts')));
assert.ok(results.some((f) => f.includes('sub2') && f.endsWith('test2.ts')));
});

test('searchLocal should find hidden files when dot option is true', async () => {
// Create hidden file
await fs.writeFile(path.join(tempDir, '.hidden.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'visible.ts'), 'content');

const results = await fileSystem.searchLocal('*.ts', tempDir, true);

assert.ok(results.length >= 2);
assert.ok(results.some((f) => f.endsWith('.hidden.ts')));
assert.ok(results.some((f) => f.endsWith('visible.ts')));
});

test('searchLocal should not find hidden files when dot option is false', async () => {
// Create hidden file
await fs.writeFile(path.join(tempDir, '.hidden.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'visible.ts'), 'content');

const results = await fileSystem.searchLocal('*.ts', tempDir, false);

assert.strictEqual(results.length, 1);
assert.ok(results.some((f) => f.endsWith('visible.ts')));
assert.ok(!results.some((f) => f.endsWith('.hidden.ts')));
});

test('searchLocal should return empty array when no files match', async () => {
const results = await fileSystem.searchLocal('*.nonexistent', tempDir);

assert.strictEqual(results.length, 0);
});

test('searchLocal should handle patterns with multiple extensions', async () => {
await fs.writeFile(path.join(tempDir, 'test.ts'), 'content');
await fs.writeFile(path.join(tempDir, 'test.js'), 'content');
await fs.writeFile(path.join(tempDir, 'test.py'), 'content');

const results = await fileSystem.searchLocal('*.{ts,js}', tempDir);

assert.strictEqual(results.length, 2);
assert.ok(results.some((f) => f.endsWith('.ts')));
assert.ok(results.some((f) => f.endsWith('.js')));
assert.ok(!results.some((f) => f.endsWith('.py')));
});
});
10 changes: 1 addition & 9 deletions src/telemetryGenerator.node.ts
Original file line number Diff line number Diff line change
Expand Up @@ -771,15 +771,7 @@ function generateTelemetryGdpr(output: TelemetryEntry[]) {
}

async function generateTelemetryOutput() {
const files = await new Promise<string[]>((resolve, reject) => {
glob(path.join(EXTENSION_ROOT_DIR_FOR_TESTS, 'src/**/*.ts'), (ex, res) => {
if (ex) {
reject(ex);
} else {
resolve(res);
}
});
});
const files = await glob(path.join(EXTENSION_ROOT_DIR_FOR_TESTS, 'src/**/*.ts'));
// Print out the source tree
return generateDocumentation(files);
}
Expand Down
12 changes: 2 additions & 10 deletions src/test/extension.serviceRegistry.vscode.test.ts
Original file line number Diff line number Diff line change
Expand Up @@ -114,16 +114,8 @@ async function getInjectableClasses(fileNames: string[], options: ts.CompilerOpt
}

async function getSourceFiles() {
const files = await new Promise<string[]>((resolve, reject) => {
const globPattern = path.join(__dirname, '..', '..', 'src', '**', '*.ts').replace(/\\/g, '/');
glob(globPattern, (ex, res) => {
if (ex) {
reject(ex);
} else {
resolve(res);
}
});
});
const globPattern = path.join(__dirname, '..', '..', 'src', '**', '*.ts').replace(/\\/g, '/');
const files = await glob(globPattern);
return files;
}

Expand Down
22 changes: 7 additions & 15 deletions src/test/index.node.ts
Original file line number Diff line number Diff line change
Expand Up @@ -187,21 +187,13 @@ export async function run(): Promise<void> {
default:
break;
}
const testFiles = await new Promise<string[]>((resolve, reject) => {
// If we have mulitple patterns, then turn into regex from `a,b,c` to `(a|b|c)`
const pattern = options.testFilesSuffix.includes(',')
? `(${options.testFilesSuffix.split(',').join('|')})`
: options.testFilesSuffix;
glob(
`**/*${pattern}.js`,
{ ignore: ['**/**.unit.test.js'].concat(ignoreGlob), cwd: testsRoot },
(error, files) => {
if (error) {
return reject(error);
}
resolve(files);
}
);
// If we have mulitple patterns, then turn into regex from `a,b,c` to `(a|b|c)`
const pattern = options.testFilesSuffix.includes(',')
? `(${options.testFilesSuffix.split(',').join('|')})`
: options.testFilesSuffix;
const testFiles = await glob(`**/*${pattern}.js`, {
ignore: ['**/**.unit.test.js'].concat(ignoreGlob),
cwd: testsRoot
});

// Setup test files that need to be run.
Expand Down
7 changes: 3 additions & 4 deletions src/test/interpreters/condaService.node.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,9 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

import glob from 'glob';
import { glob } from 'glob';
import * as path from '../../platform/vscode-path/path';
import { parse, SemVer } from 'semver';
import { promisify } from 'util';
import { logger } from '../../platform/logging';
import { arePathsSame } from '../../platform/common/platform/fileUtils.node';
import { ProcessService } from '../../platform/common/process/proc.node';
Expand Down Expand Up @@ -65,14 +64,14 @@ const CondaLocationsGlobWin = `{${condaGlobPathsForWindows.join(',')}}`;
*/
async function getCondaFileFromKnownLocations(): Promise<string> {
const globPattern = getOSType() === OSType.Windows ? CondaLocationsGlobWin : CondaLocationsGlob;
const condaFiles = await promisify(glob)(globPattern).catch<string[]>((failReason) => {
const condaFiles = await glob(globPattern, {}).catch<string[]>((failReason) => {
logger.warn(
'Default conda location search failed.',
`Searching for default install locations for conda results in error: ${failReason}`
);
return [];
});
const validCondaFiles = condaFiles.filter((condaPath) => condaPath.length > 0);
const validCondaFiles = condaFiles.filter((condaPath: string) => condaPath.length > 0);
return validCondaFiles.length === 0 ? 'conda' : validCondaFiles[0];
}

Expand Down
92 changes: 92 additions & 0 deletions src/test/interpreters/condaService.node.unit.test.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,92 @@
// Copyright (c) Microsoft Corporation.
// Licensed under the MIT License.

/* eslint-disable local-rules/dont-use-process */

import { assert } from 'chai';
import * as path from '../../platform/vscode-path/path';
import * as fs from 'fs-extra';
import * as os from 'os';
import { getCondaFile } from './condaService.node';
import { glob } from 'glob';

suite('condaService - glob functionality', () => {
let originalEnv: string | undefined;
let tempDir: string;

setup(async () => {
// Save original environment variable
originalEnv = process.env.CI_PYTHON_CONDA_PATH;
delete process.env.CI_PYTHON_CONDA_PATH;

// Create a temporary directory for testing
tempDir = await fs.mkdtemp(path.join(os.tmpdir(), 'conda-test-'));
});

teardown(async () => {
// Restore environment variable
if (originalEnv !== undefined) {
process.env.CI_PYTHON_CONDA_PATH = originalEnv;
} else {
delete process.env.CI_PYTHON_CONDA_PATH;
}

// Clean up temp directory
await fs.remove(tempDir);
});

test('getCondaFile should use CI_PYTHON_CONDA_PATH when set', async () => {
process.env.CI_PYTHON_CONDA_PATH = '/custom/conda/path';

const result = await getCondaFile();

assert.strictEqual(result, '/custom/conda/path');
});

test('glob should work with basic patterns', async () => {
// Create test files
await fs.writeFile(path.join(tempDir, 'conda'), 'test');
await fs.writeFile(path.join(tempDir, 'python'), 'test');

const results = await glob('conda', { cwd: tempDir });

assert.strictEqual(results.length, 1);
assert.ok(results[0].includes('conda'));
});

test('glob should work with wildcard patterns', async () => {
// Create test files
await fs.writeFile(path.join(tempDir, 'conda1'), 'test');
await fs.writeFile(path.join(tempDir, 'conda2'), 'test');
await fs.writeFile(path.join(tempDir, 'python'), 'test');

const results = await glob('conda*', { cwd: tempDir });

assert.strictEqual(results.length, 2);
});

test('glob should handle brace expansion patterns', async () => {
// Create test files
await fs.writeFile(path.join(tempDir, 'conda'), 'test');
await fs.writeFile(path.join(tempDir, 'miniconda'), 'test');
await fs.writeFile(path.join(tempDir, 'python'), 'test');

const results = await glob('{conda,miniconda}', { cwd: tempDir });

assert.strictEqual(results.length, 2);
assert.ok(results.some((r) => r.includes('conda')));
assert.ok(results.some((r) => r.includes('miniconda')));
});

test('glob should return empty array when no matches found', async () => {
const results = await glob('nonexistent*', { cwd: tempDir });

assert.strictEqual(results.length, 0);
});

test('glob should handle errors gracefully with catch', async () => {
const results = await glob('/nonexistent/path/**/*', {}).catch(() => []);

assert.deepStrictEqual(results, []);
});
});
Loading