Skip to content

feat: Table data grouping (experiment)#128

Closed
pan-kot wants to merge 6 commits intomainfrom
table-data-grouping-2
Closed

feat: Table data grouping (experiment)#128
pan-kot wants to merge 6 commits intomainfrom
table-data-grouping-2

Conversation

@pan-kot
Copy link
Copy Markdown
Member

@pan-kot pan-kot commented Jan 26, 2026

Same as #126, but with selection tree and track-by utils coming from the toolkit.

By submitting this pull request, I confirm that you can use, modify, copy, and redistribute this contribution, under the terms of your choice.

@pan-kot pan-kot changed the title Table data grouping 2 feat: Table data grouping (experiment) Jan 26, 2026

function execCommand(command, options = {}) {
try {
execSync(command, { stdio: 'inherit', ...options });

Check warning

Code scanning / CodeQL

Shell command built from environment values Medium

This shell command depends on an uncontrolled
absolute path
.

Copilot Autofix

AI 2 months ago

In general, the safest fix is to avoid constructing full shell command strings and instead invoke commands directly with argument arrays, so the shell never interprets the dynamic values. For Node, that means replacing execSync(commandString) with execFileSync(binary, argsArray, options) (or spawnSync). Each dynamic path or branch name then becomes an element of the args array, and execFileSync does not go through a shell by default.

For this file, the best targeted change is:

  • Replace the generic execCommand(command, options) helper with a helper that accepts a command name and an array of arguments and calls execFileSync.
  • Update all call sites:
    • git clone ${targetRepository} ${tempDir}execCommand('git', ['clone', targetRepository, tempDir])
    • git checkout ${targetBranch}execCommand('git', ['checkout', targetBranch])
    • npm installexecCommand('npm', ['install'])
    • npm run buildexecCommand('npm', ['run', 'build'])
    • rm -rf ${modulePath}execCommand('rm', ['-rf', modulePath])
    • mkdir -p ${modulePath}execCommand('mkdir', ['-p', modulePath])
    • cp -R ${tempDir}${artifactPath} ${modulePath}execCommand('cp', ['-R', ${tempDir}${artifactPath}, modulePath])
    • rm -rf ${tempDir}execCommand('rm', ['-rf', tempDir])
  • Adjust logging to reflect the new argument style, but keep functionality the same.
  • Import execFileSync from child_process in addition to (or instead of) execSync. We can retain execSync if needed elsewhere, but in this snippet we only use the new helper.

All edits are confined to scripts/install-peer-dependency.js: updating the import on line 9, replacing the execCommand definition at the bottom, and updating each execCommand(...) call between lines 54 and 79.

Suggested changeset 1
scripts/install-peer-dependency.js

Autofix patch

Autofix patch
Run the following command in your local git repository to apply this patch
cat << 'EOF' | git apply
diff --git a/scripts/install-peer-dependency.js b/scripts/install-peer-dependency.js
--- a/scripts/install-peer-dependency.js
+++ b/scripts/install-peer-dependency.js
@@ -6,7 +6,7 @@
 // "postinstall": "node ./scripts/install-peer-dependency.js collection-hooks:property-filter-token-groups"
 // where "collection-hooks" is the package to fetch and "property-filter-token-groups" is the branch name in GitHub.
 
-import { execSync } from 'child_process';
+import { execFileSync } from 'child_process';
 import process from 'node:process';
 import os from 'os';
 import path from 'path';
@@ -51,14 +51,14 @@
 
 // Clone the repository and checkout the branch
 console.log(`Cloning ${packageName}:${targetBranch}...`);
-execCommand(`git clone ${targetRepository} ${tempDir}`);
+execCommand('git', ['clone', targetRepository, tempDir]);
 process.chdir(tempDir);
-execCommand(`git checkout ${targetBranch}`);
+execCommand('git', ['checkout', targetBranch]);
 
 // Install dependencies and build
 console.log(`Installing dependencies and building ${packageName}...`);
-execCommand('npm install');
-execCommand('npm run build');
+execCommand('npm', ['install']);
+execCommand('npm', ['run', 'build']);
 
 // Remove existing peer dependency in node_modules
 for (const moduleName of getModules(packageName)) {
@@ -66,25 +62,25 @@
   const artifactPath = getArtifactPath(moduleName);
 
   console.log(`Removing existing ${moduleName} from node_modules...`, modulePath);
-  execCommand(`rm -rf ${modulePath}`);
+  execCommand('rm', ['-rf', modulePath]);
 
   // Copy built peer dependency to node_modules
   console.log(`Copying built ${moduleName} to node_modules...`, modulePath, `${tempDir}${artifactPath}`);
-  execCommand(`mkdir -p ${modulePath}`);
-  execCommand(`cp -R ${tempDir}${artifactPath} ${modulePath}`);
+  execCommand('mkdir', ['-p', modulePath]);
+  execCommand('cp', ['-R', `${tempDir}${artifactPath}`, modulePath]);
 }
 
 // Clean up
 console.log('Cleaning up...');
-execCommand(`rm -rf ${tempDir}`);
+execCommand('rm', ['-rf', tempDir]);
 
 console.log(`${packageName} has been successfully installed from branch ${targetBranch}!`);
 
-function execCommand(command, options = {}) {
+function execCommand(command, args = [], options = {}) {
   try {
-    execSync(command, { stdio: 'inherit', ...options });
+    execFileSync(command, args, { stdio: 'inherit', ...options });
   } catch (error) {
-    console.error(`Error executing command: ${command}`);
+    console.error(`Error executing command: ${command} ${args.join(' ')}`);
     console.error(`Error message: ${error.message}`);
     console.error(`Stdout: ${error.stdout && error.stdout.toString()}`);
     console.error(`Stderr: ${error.stderr && error.stderr.toString()}`);
EOF
@@ -6,7 +6,7 @@
// "postinstall": "node ./scripts/install-peer-dependency.js collection-hooks:property-filter-token-groups"
// where "collection-hooks" is the package to fetch and "property-filter-token-groups" is the branch name in GitHub.

import { execSync } from 'child_process';
import { execFileSync } from 'child_process';
import process from 'node:process';
import os from 'os';
import path from 'path';
@@ -51,14 +51,14 @@

// Clone the repository and checkout the branch
console.log(`Cloning ${packageName}:${targetBranch}...`);
execCommand(`git clone ${targetRepository} ${tempDir}`);
execCommand('git', ['clone', targetRepository, tempDir]);
process.chdir(tempDir);
execCommand(`git checkout ${targetBranch}`);
execCommand('git', ['checkout', targetBranch]);

// Install dependencies and build
console.log(`Installing dependencies and building ${packageName}...`);
execCommand('npm install');
execCommand('npm run build');
execCommand('npm', ['install']);
execCommand('npm', ['run', 'build']);

// Remove existing peer dependency in node_modules
for (const moduleName of getModules(packageName)) {
@@ -66,25 +62,25 @@
const artifactPath = getArtifactPath(moduleName);

console.log(`Removing existing ${moduleName} from node_modules...`, modulePath);
execCommand(`rm -rf ${modulePath}`);
execCommand('rm', ['-rf', modulePath]);

// Copy built peer dependency to node_modules
console.log(`Copying built ${moduleName} to node_modules...`, modulePath, `${tempDir}${artifactPath}`);
execCommand(`mkdir -p ${modulePath}`);
execCommand(`cp -R ${tempDir}${artifactPath} ${modulePath}`);
execCommand('mkdir', ['-p', modulePath]);
execCommand('cp', ['-R', `${tempDir}${artifactPath}`, modulePath]);
}

// Clean up
console.log('Cleaning up...');
execCommand(`rm -rf ${tempDir}`);
execCommand('rm', ['-rf', tempDir]);

console.log(`${packageName} has been successfully installed from branch ${targetBranch}!`);

function execCommand(command, options = {}) {
function execCommand(command, args = [], options = {}) {
try {
execSync(command, { stdio: 'inherit', ...options });
execFileSync(command, args, { stdio: 'inherit', ...options });
} catch (error) {
console.error(`Error executing command: ${command}`);
console.error(`Error executing command: ${command} ${args.join(' ')}`);
console.error(`Error message: ${error.message}`);
console.error(`Stdout: ${error.stdout && error.stdout.toString()}`);
console.error(`Stderr: ${error.stderr && error.stderr.toString()}`);
Copilot is powered by AI and may make mistakes. Always verify output.
@pan-kot pan-kot force-pushed the table-data-grouping-2 branch 3 times, most recently from 1af2027 to 302a0ac Compare January 26, 2026 10:46
@pan-kot pan-kot force-pushed the table-data-grouping-2 branch from 302a0ac to b84bb22 Compare January 26, 2026 11:09
@codecov
Copy link
Copy Markdown

codecov bot commented Jan 26, 2026

Codecov Report

✅ All modified and coverable lines are covered by tests.
✅ Project coverage is 100.00%. Comparing base (3ca9920) to head (b84bb22).

Additional details and impacted files
@@             Coverage Diff             @@
##             main      #128      +/-   ##
===========================================
+ Coverage   98.59%   100.00%   +1.40%     
===========================================
  Files          16        13       -3     
  Lines         498       418      -80     
  Branches      171       156      -15     
===========================================
- Hits          491       418      -73     
+ Misses          5         0       -5     
+ Partials        2         0       -2     

☔ View full report in Codecov by Sentry.
📢 Have feedback on the report? Share it here.

🚀 New features to boost your workflow:
  • ❄️ Test Analytics: Detect flaky tests, report on failures, and find test suite problems.
  • 📦 JS Bundle Analysis: Save yourself from yourself by tracking and limiting bundle sizes in JS merges.

@pan-kot pan-kot closed this Jan 26, 2026
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant