File tree Expand file tree Collapse file tree
Expand file tree Collapse file tree Original file line number Diff line number Diff line change 66 pull_request :
77 branches : [main]
88
9+ permissions :
10+ contents : read
11+
912jobs :
1013 test :
1114 runs-on : ubuntu-latest
Original file line number Diff line number Diff line change 11import { describe , expect , it } from "vitest" ;
2- import { sanitizeToolName } from "@execbox/core" ;
2+ import { sanitizeIdentifier , sanitizeToolName } from "@execbox/core" ;
33
44describe ( "sanitizeToolName" , ( ) => {
55 it ( "replaces punctuation and spaces with underscores" , ( ) => {
@@ -18,3 +18,17 @@ describe("sanitizeToolName", () => {
1818 expect ( sanitizeToolName ( "" ) ) . toBe ( "_" ) ;
1919 } ) ;
2020} ) ;
21+
22+ describe ( "sanitizeIdentifier" , ( ) => {
23+ it ( "removes leading and trailing replacement underscores" , ( ) => {
24+ expect ( sanitizeIdentifier ( " ---tool name--- " ) ) . toBe ( "tool_name" ) ;
25+ } ) ;
26+
27+ it ( "preserves internal underscores while trimming the edges" , ( ) => {
28+ expect ( sanitizeIdentifier ( "tool---name" ) ) . toBe ( "tool_name" ) ;
29+ } ) ;
30+
31+ it ( "falls back to an underscore when all characters are trimmed away" , ( ) => {
32+ expect ( sanitizeIdentifier ( "---" ) ) . toBe ( "_" ) ;
33+ } ) ;
34+ } ) ;
Original file line number Diff line number Diff line change 1+ import { readFileSync } from "node:fs" ;
2+ import { describe , expect , it } from "vitest" ;
3+
4+ describe ( "ci workflow" , ( ) => {
5+ it ( "declares least-privilege GITHUB_TOKEN permissions" , ( ) => {
6+ const workflow = readFileSync (
7+ new URL ( "../../../../.github/workflows/ci.yml" , import . meta. url ) ,
8+ "utf8" ,
9+ ) ;
10+
11+ expect ( workflow ) . toContain ( "permissions:" ) ;
12+ expect ( workflow ) . toContain ( "contents: read" ) ;
13+ } ) ;
14+ } ) ;
Original file line number Diff line number Diff line change @@ -39,6 +39,23 @@ const RESERVED_WORDS = new Set([
3939 "yield" ,
4040] ) ;
4141
42+ const UNDERSCORE_CHAR_CODE = 95 ;
43+
44+ function trimEdgeUnderscores ( value : string ) : string {
45+ let start = 0 ;
46+ let end = value . length ;
47+
48+ while ( start < end && value . charCodeAt ( start ) === UNDERSCORE_CHAR_CODE ) {
49+ start += 1 ;
50+ }
51+
52+ while ( end > start && value . charCodeAt ( end - 1 ) === UNDERSCORE_CHAR_CODE ) {
53+ end -= 1 ;
54+ }
55+
56+ return value . slice ( start , end ) ;
57+ }
58+
4259/**
4360 * Returns whether the value is a valid JavaScript identifier.
4461 */
@@ -69,12 +86,11 @@ export function assertValidIdentifier(
6986 * Converts a raw identifier-like value into a safe JavaScript identifier.
7087 */
7188export function sanitizeIdentifier ( value : string ) : string {
72- const sanitized = value
73- . trim ( )
74- . replace ( / [ ^ A - Z a - z 0 - 9 _ $ ] + / g, "_" )
75- . replace ( / ^ _ + | _ + $ / g, "" ) ;
89+ const sanitized = value . trim ( ) . replace ( / [ ^ A - Z a - z 0 - 9 _ $ ] + / g, "_" ) ;
90+
91+ const trimmed = trimEdgeUnderscores ( sanitized ) ;
7692
77- let safeName = sanitized . length > 0 ? sanitized : "_" ;
93+ let safeName = trimmed . length > 0 ? trimmed : "_" ;
7894
7995 if ( / ^ [ 0 - 9 ] / . test ( safeName ) ) {
8096 safeName = `_${ safeName } ` ;
You can’t perform that action at this time.
0 commit comments