@marko/language-tools 2.0.11 → 2.1.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
@@ -0,0 +1,10 @@
1
+ import { Parsed } from "../../parser";
2
+ export declare function extractHTML(parsed: Parsed): {
3
+ extracted: import("../../util/extractor").Extracted;
4
+ nodeDetails: {
5
+ [id: string]: {
6
+ hasDynamicAttrs: boolean;
7
+ hasDynamicBody: boolean;
8
+ };
9
+ };
10
+ };
@@ -0,0 +1,8 @@
1
+ export declare function isHTMLTag(tag: string): boolean;
2
+ export declare enum AttributeValueType {
3
+ True = 0,
4
+ Literal = 1,
5
+ QuotedString = 2,
6
+ Dynamic = 3
7
+ }
8
+ export declare function getAttributeValueType(value: string | undefined): AttributeValueType | undefined;
package/dist/index.d.ts CHANGED
@@ -5,4 +5,5 @@ export * as Project from "./util/project";
5
5
  export * as Processors from "./processors";
6
6
  export { getExt } from "./util/get-ext";
7
7
  export { isDefinitionFile } from "./util/is-definition-file";
8
+ export * from "./extractors/html";
8
9
  export { type Extracted } from "./util/extractor";
package/dist/index.js CHANGED
@@ -35,6 +35,7 @@ __export(src_exports, {
35
35
  Project: () => project_exports,
36
36
  ScriptLang: () => ScriptLang,
37
37
  UNFINISHED: () => UNFINISHED,
38
+ extractHTML: () => extractHTML,
38
39
  extractScript: () => extractScript,
39
40
  extractStyle: () => extractStyle,
40
41
  getExt: () => getExt,
@@ -2931,24 +2932,12 @@ __export(project_exports, {
2931
2932
  });
2932
2933
  var import_path2 = __toESM(require("path"));
2933
2934
  var import_module = require("module");
2934
- var defaultCompiler = __toESM(require("@marko/compiler"));
2935
- var defaultConfig = __toESM(require("@marko/compiler/config"));
2936
- var defaultTranslator = __toESM(require("@marko/translator-default"));
2937
2935
  var import_strip_json_comments = __toESM(require("strip-json-comments"));
2938
2936
  var defaultTypeLibs = {};
2939
2937
  var ignoreErrors = (_err) => {
2940
2938
  };
2941
2939
  var metaByDir = /* @__PURE__ */ new Map();
2942
2940
  var metaByCompiler = /* @__PURE__ */ new Map();
2943
- var defaultMeta = {
2944
- compiler: defaultCompiler,
2945
- config: {
2946
- ...defaultConfig,
2947
- cache: /* @__PURE__ */ new Map(),
2948
- translator: defaultTranslator
2949
- }
2950
- };
2951
- defaultCompiler.configure(defaultMeta.config);
2952
2941
  function getCompiler(dir) {
2953
2942
  return getMeta(dir).compiler;
2954
2943
  }
@@ -3050,7 +3039,6 @@ function getScriptLang(fileName, defaultScriptLang, ts, host) {
3050
3039
  return scriptLang;
3051
3040
  }
3052
3041
  function clearCaches() {
3053
- clearCacheForMeta(defaultMeta);
3054
3042
  for (const project of metaByCompiler.values()) {
3055
3043
  clearCacheForMeta(project);
3056
3044
  }
@@ -3058,24 +3046,22 @@ function clearCaches() {
3058
3046
  function setDefaultTypePaths(defaults) {
3059
3047
  Object.assign(defaultTypeLibs, defaults);
3060
3048
  }
3061
- function getMeta(dir) {
3062
- if (!dir)
3063
- return defaultMeta;
3049
+ function getMeta(dir = __dirname) {
3064
3050
  let cached = metaByDir.get(dir);
3065
3051
  if (!cached) {
3052
+ const fallback = dir === __dirname;
3066
3053
  try {
3067
3054
  const require2 = (0, import_module.createRequire)(dir);
3068
- const compilerConfigPath = require2.resolve("@marko/compiler/config");
3069
- cached = metaByCompiler.get(compilerConfigPath);
3055
+ const configPath = require2.resolve("@marko/compiler/config");
3056
+ cached = metaByCompiler.get(configPath);
3070
3057
  if (!cached) {
3071
3058
  const compiler = require2(import_path2.default.join(
3072
- compilerConfigPath,
3059
+ configPath,
3073
3060
  ".."
3074
3061
  ));
3075
- const config = interopDefault(
3076
- require2(compilerConfigPath)
3077
- );
3062
+ const config = interopDefault(require2(configPath));
3078
3063
  cached = {
3064
+ fallback,
3079
3065
  compiler,
3080
3066
  config: {
3081
3067
  ...config,
@@ -3084,10 +3070,12 @@ function getMeta(dir) {
3084
3070
  }
3085
3071
  };
3086
3072
  compiler.configure(cached.config);
3087
- metaByCompiler.set(compilerConfigPath, cached);
3073
+ metaByCompiler.set(configPath, cached);
3088
3074
  }
3089
- } catch {
3090
- cached = defaultMeta;
3075
+ } catch (err) {
3076
+ if (fallback)
3077
+ throw err;
3078
+ cached = getMeta();
3091
3079
  }
3092
3080
  metaByDir.set(dir, cached);
3093
3081
  }
@@ -3104,8 +3092,8 @@ function getTagLookupForProject(meta, dir) {
3104
3092
  ignoreErrors
3105
3093
  );
3106
3094
  } catch {
3107
- if (meta !== defaultMeta) {
3108
- lookup = getTagLookupForProject(defaultMeta, dir);
3095
+ if (!meta.fallback) {
3096
+ lookup = getTagLookupForProject(getMeta(), dir);
3109
3097
  }
3110
3098
  }
3111
3099
  if (cache) {
@@ -3319,6 +3307,170 @@ function has(fileName) {
3319
3307
  function isDefinitionFile(fileName) {
3320
3308
  return /\.d\.[^.]+$/.test(fileName);
3321
3309
  }
3310
+
3311
+ // src/extractors/html/keywords.ts
3312
+ var builtinTagsRegex = /^(?:a(?:(?:bbr|cronym|ddress|pplet|r(?:ea|ticle)|side|udio))?|b(?:(?:ase(?:font)?|d[io]|gsound|ig|l(?:ink|ockquote)|ody|r|utton))?|c(?:a(?:nvas|ption)|enter|ite|o(?:de|l(?:group)?|mmand|ntent))|d(?:ata(?:list)?|d|e(?:l|tails)|fn|i(?:alog|r|v)|l|t)|e(?:lement|m(?:bed)?)|f(?:i(?:eldset|g(?:caption|ure))|o(?:nt|oter|rm)|rame(?:set)?)|h(?:1|2|3|4|5|6|ead(?:er)?|group|r|tml)|i(?:(?:frame|m(?:age|g)|n(?:put|s)|sindex))?|k(?:bd|eygen)|l(?:abel|egend|i(?:(?:nk|sting))?)|m(?:a(?:in|p|r(?:k|quee)|th)|e(?:nu(?:item)?|t(?:a|er))|ulticol)|n(?:av|extid|o(?:br|embed|frames|script))|o(?:bject|l|pt(?:group|ion)|utput)|p(?:(?:aram|icture|laintext|r(?:e|ogress)))?|q|r(?:bc?|p|tc?|uby)|s(?:(?:amp|cript|e(?:ction|lect)|hadow|lot|mall|ource|pa(?:cer|n)|t(?:r(?:ike|ong)|yle)|u(?:b|mmary|p)|vg))?|t(?:able|body|d|e(?:mplate|xtarea)|foot|h(?:ead)?|i(?:me|tle)|r(?:ack)?|t)|ul?|v(?:ar|ideo)|wbr|xmp)$/;
3313
+ function isHTMLTag(tag) {
3314
+ return builtinTagsRegex.test(tag);
3315
+ }
3316
+ function getAttributeValueType(value) {
3317
+ if (value === void 0 || value[0] !== "=")
3318
+ return void 0;
3319
+ value = value.substring(1).trim();
3320
+ switch (value) {
3321
+ case "NaN":
3322
+ case "Infinity":
3323
+ case "-Infinity":
3324
+ return 1 /* Literal */;
3325
+ case "null":
3326
+ case "false":
3327
+ case "undefined":
3328
+ return void 0;
3329
+ case "true":
3330
+ return 0 /* True */;
3331
+ }
3332
+ if (
3333
+ // double quote string
3334
+ /^"(?:[^"\\]+|\\.)*"$/.test(value) || // single quote string
3335
+ /^'(?:[^'\\]+|\\.)*'$/.test(value) || // template literal without any interpolations
3336
+ /^`(?:[^`\\$]+|\\.|\$(?!\{))*`$/.test(value)
3337
+ ) {
3338
+ return 2 /* QuotedString */;
3339
+ } else if (
3340
+ // octal literal
3341
+ /^-?0[oO]?[0-7](?:_?[0-7]+)*n?$/.test(value) || // hex literal
3342
+ /^-?0[xX][0-9a-fA-F](?:_?[0-9a-fA-F]+)*n?$/.test(value) || // binary literal
3343
+ /^-?0[bB][01](?:_?[01]+)*n?$/.test(value) || // integer or float
3344
+ /^-?\d(?:_?\d+)*(?:[.eE]\d(?:_?\d+)*|n?|\.?)$/.test(value)
3345
+ ) {
3346
+ return 1 /* Literal */;
3347
+ }
3348
+ return 3 /* Dynamic */;
3349
+ }
3350
+
3351
+ // src/extractors/html/index.ts
3352
+ function extractHTML(parsed) {
3353
+ return new HTMLExtractor(parsed).end();
3354
+ }
3355
+ var HTMLExtractor = class {
3356
+ #extractor;
3357
+ #read;
3358
+ #nodeDetails;
3359
+ #nodeIdCounter;
3360
+ #dynamicAttrValueCounter;
3361
+ constructor(parsed) {
3362
+ this.#extractor = new Extractor(parsed);
3363
+ this.#read = parsed.read.bind(parsed);
3364
+ this.#nodeDetails = {};
3365
+ this.#nodeIdCounter = 0;
3366
+ this.#dynamicAttrValueCounter = 0;
3367
+ parsed.program.body.forEach((node) => this.#visitNode(node));
3368
+ }
3369
+ end() {
3370
+ return { extracted: this.#extractor.end(), nodeDetails: this.#nodeDetails };
3371
+ }
3372
+ #visitNode(node) {
3373
+ var _a;
3374
+ let hasDynamicBody = false, hasDynamicAttrs = false, isDynamic = false;
3375
+ switch (node.type) {
3376
+ case 16 /* AttrTag */:
3377
+ (_a = node.body) == null ? void 0 : _a.forEach((child) => {
3378
+ if (this.#visitNode(child))
3379
+ hasDynamicBody = true;
3380
+ });
3381
+ break;
3382
+ case 1 /* Tag */: {
3383
+ const nodeId = `${this.#nodeIdCounter++}`;
3384
+ ({ isDynamic, hasDynamicAttrs, hasDynamicBody } = this.#writeTag(
3385
+ node,
3386
+ nodeId
3387
+ ));
3388
+ this.#nodeDetails[nodeId] = { hasDynamicAttrs, hasDynamicBody };
3389
+ break;
3390
+ }
3391
+ case 17 /* Text */:
3392
+ this.#extractor.copy(node);
3393
+ break;
3394
+ case 22 /* Placeholder */:
3395
+ isDynamic = this.#read({
3396
+ start: node.start + 1,
3397
+ end: node.start + 2
3398
+ }) === "!";
3399
+ }
3400
+ return isDynamic || hasDynamicBody;
3401
+ }
3402
+ #writeTag(node, id) {
3403
+ const isDynamic = !node.nameText || !isHTMLTag(node.nameText);
3404
+ let hasDynamicAttrs = false, hasDynamicBody = false;
3405
+ if (!isDynamic) {
3406
+ ({ hasDynamicAttrs, hasDynamicBody } = this.#writeHTMLTag(node, id));
3407
+ } else {
3408
+ this.#writeCustomTag(node);
3409
+ }
3410
+ return { isDynamic, hasDynamicAttrs, hasDynamicBody };
3411
+ }
3412
+ #writeHTMLTag(node, id) {
3413
+ var _a, _b;
3414
+ let hasDynamicAttrs = false, hasDynamicBody = false;
3415
+ this.#extractor.write("<");
3416
+ this.#extractor.copy(node.name);
3417
+ this.#extractor.write(` data-marko-node-id="${id}"`);
3418
+ (_a = node.attrs) == null ? void 0 : _a.forEach((attr) => {
3419
+ if (attr.type === 10 /* AttrNamed */)
3420
+ this.#writeAttrNamed(attr);
3421
+ else if (attr.type === 15 /* AttrSpread */)
3422
+ hasDynamicAttrs = true;
3423
+ });
3424
+ this.#extractor.write(">");
3425
+ (_b = node.body) == null ? void 0 : _b.forEach((child) => {
3426
+ if (this.#visitNode(child))
3427
+ hasDynamicBody = true;
3428
+ });
3429
+ this.#extractor.write(`</${node.nameText}>`);
3430
+ return { hasDynamicAttrs, hasDynamicBody };
3431
+ }
3432
+ #writeCustomTag(node) {
3433
+ if (node.body) {
3434
+ this.#extractor.write("<div>");
3435
+ node.body.forEach((node2) => this.#visitNode(node2));
3436
+ this.#extractor.write("</div>");
3437
+ }
3438
+ }
3439
+ #writeAttrNamed(attr) {
3440
+ this.#extractor.write(" ");
3441
+ this.#extractor.copy(attr.name);
3442
+ if (attr.value === void 0 || attr.name.start === attr.name.end || attr.value.type === 14 /* AttrMethod */) {
3443
+ return;
3444
+ }
3445
+ const valueString = this.#read(attr.value);
3446
+ const valueType = getAttributeValueType(valueString);
3447
+ if (valueType === void 0)
3448
+ return;
3449
+ switch (valueType) {
3450
+ case 0 /* True */:
3451
+ break;
3452
+ case 1 /* Literal */:
3453
+ this.#extractor.write('="');
3454
+ this.#extractor.copy({
3455
+ start: attr.value.start + valueString.search(/[^=\s]/g),
3456
+ end: attr.value.end
3457
+ });
3458
+ this.#extractor.write('"');
3459
+ break;
3460
+ case 2 /* QuotedString */:
3461
+ this.#extractor.write('="');
3462
+ this.#extractor.copy({
3463
+ start: attr.value.start + valueString.search(/[^=\s]/g) + 1,
3464
+ end: attr.value.end - 1
3465
+ });
3466
+ this.#extractor.write('"');
3467
+ break;
3468
+ case 3 /* Dynamic */:
3469
+ this.#extractor.write(`="dynamic${this.#dynamicAttrValueCounter++}"`);
3470
+ break;
3471
+ }
3472
+ }
3473
+ };
3322
3474
  // Annotate the CommonJS export names for ESM import in node:
3323
3475
  0 && (module.exports = {
3324
3476
  NodeType,
@@ -3326,6 +3478,7 @@ function isDefinitionFile(fileName) {
3326
3478
  Project,
3327
3479
  ScriptLang,
3328
3480
  UNFINISHED,
3481
+ extractHTML,
3329
3482
  extractScript,
3330
3483
  extractStyle,
3331
3484
  getExt,
package/dist/index.mjs CHANGED
@@ -2900,24 +2900,12 @@ __export(project_exports, {
2900
2900
  });
2901
2901
  import path2 from "path";
2902
2902
  import { createRequire } from "module";
2903
- import * as defaultCompiler from "@marko/compiler";
2904
- import * as defaultConfig from "@marko/compiler/config";
2905
- import * as defaultTranslator from "@marko/translator-default";
2906
2903
  import stripJSONComments from "strip-json-comments";
2907
2904
  var defaultTypeLibs = {};
2908
2905
  var ignoreErrors = (_err) => {
2909
2906
  };
2910
2907
  var metaByDir = /* @__PURE__ */ new Map();
2911
2908
  var metaByCompiler = /* @__PURE__ */ new Map();
2912
- var defaultMeta = {
2913
- compiler: defaultCompiler,
2914
- config: {
2915
- ...defaultConfig,
2916
- cache: /* @__PURE__ */ new Map(),
2917
- translator: defaultTranslator
2918
- }
2919
- };
2920
- defaultCompiler.configure(defaultMeta.config);
2921
2909
  function getCompiler(dir) {
2922
2910
  return getMeta(dir).compiler;
2923
2911
  }
@@ -3019,7 +3007,6 @@ function getScriptLang(fileName, defaultScriptLang, ts, host) {
3019
3007
  return scriptLang;
3020
3008
  }
3021
3009
  function clearCaches() {
3022
- clearCacheForMeta(defaultMeta);
3023
3010
  for (const project of metaByCompiler.values()) {
3024
3011
  clearCacheForMeta(project);
3025
3012
  }
@@ -3027,24 +3014,22 @@ function clearCaches() {
3027
3014
  function setDefaultTypePaths(defaults) {
3028
3015
  Object.assign(defaultTypeLibs, defaults);
3029
3016
  }
3030
- function getMeta(dir) {
3031
- if (!dir)
3032
- return defaultMeta;
3017
+ function getMeta(dir = __dirname) {
3033
3018
  let cached = metaByDir.get(dir);
3034
3019
  if (!cached) {
3020
+ const fallback = dir === __dirname;
3035
3021
  try {
3036
3022
  const require2 = createRequire(dir);
3037
- const compilerConfigPath = require2.resolve("@marko/compiler/config");
3038
- cached = metaByCompiler.get(compilerConfigPath);
3023
+ const configPath = require2.resolve("@marko/compiler/config");
3024
+ cached = metaByCompiler.get(configPath);
3039
3025
  if (!cached) {
3040
3026
  const compiler = require2(path2.join(
3041
- compilerConfigPath,
3027
+ configPath,
3042
3028
  ".."
3043
3029
  ));
3044
- const config = interopDefault(
3045
- require2(compilerConfigPath)
3046
- );
3030
+ const config = interopDefault(require2(configPath));
3047
3031
  cached = {
3032
+ fallback,
3048
3033
  compiler,
3049
3034
  config: {
3050
3035
  ...config,
@@ -3053,10 +3038,12 @@ function getMeta(dir) {
3053
3038
  }
3054
3039
  };
3055
3040
  compiler.configure(cached.config);
3056
- metaByCompiler.set(compilerConfigPath, cached);
3041
+ metaByCompiler.set(configPath, cached);
3057
3042
  }
3058
- } catch {
3059
- cached = defaultMeta;
3043
+ } catch (err) {
3044
+ if (fallback)
3045
+ throw err;
3046
+ cached = getMeta();
3060
3047
  }
3061
3048
  metaByDir.set(dir, cached);
3062
3049
  }
@@ -3073,8 +3060,8 @@ function getTagLookupForProject(meta, dir) {
3073
3060
  ignoreErrors
3074
3061
  );
3075
3062
  } catch {
3076
- if (meta !== defaultMeta) {
3077
- lookup = getTagLookupForProject(defaultMeta, dir);
3063
+ if (!meta.fallback) {
3064
+ lookup = getTagLookupForProject(getMeta(), dir);
3078
3065
  }
3079
3066
  }
3080
3067
  if (cache) {
@@ -3288,12 +3275,177 @@ function has(fileName) {
3288
3275
  function isDefinitionFile(fileName) {
3289
3276
  return /\.d\.[^.]+$/.test(fileName);
3290
3277
  }
3278
+
3279
+ // src/extractors/html/keywords.ts
3280
+ var builtinTagsRegex = /^(?:a(?:(?:bbr|cronym|ddress|pplet|r(?:ea|ticle)|side|udio))?|b(?:(?:ase(?:font)?|d[io]|gsound|ig|l(?:ink|ockquote)|ody|r|utton))?|c(?:a(?:nvas|ption)|enter|ite|o(?:de|l(?:group)?|mmand|ntent))|d(?:ata(?:list)?|d|e(?:l|tails)|fn|i(?:alog|r|v)|l|t)|e(?:lement|m(?:bed)?)|f(?:i(?:eldset|g(?:caption|ure))|o(?:nt|oter|rm)|rame(?:set)?)|h(?:1|2|3|4|5|6|ead(?:er)?|group|r|tml)|i(?:(?:frame|m(?:age|g)|n(?:put|s)|sindex))?|k(?:bd|eygen)|l(?:abel|egend|i(?:(?:nk|sting))?)|m(?:a(?:in|p|r(?:k|quee)|th)|e(?:nu(?:item)?|t(?:a|er))|ulticol)|n(?:av|extid|o(?:br|embed|frames|script))|o(?:bject|l|pt(?:group|ion)|utput)|p(?:(?:aram|icture|laintext|r(?:e|ogress)))?|q|r(?:bc?|p|tc?|uby)|s(?:(?:amp|cript|e(?:ction|lect)|hadow|lot|mall|ource|pa(?:cer|n)|t(?:r(?:ike|ong)|yle)|u(?:b|mmary|p)|vg))?|t(?:able|body|d|e(?:mplate|xtarea)|foot|h(?:ead)?|i(?:me|tle)|r(?:ack)?|t)|ul?|v(?:ar|ideo)|wbr|xmp)$/;
3281
+ function isHTMLTag(tag) {
3282
+ return builtinTagsRegex.test(tag);
3283
+ }
3284
+ function getAttributeValueType(value) {
3285
+ if (value === void 0 || value[0] !== "=")
3286
+ return void 0;
3287
+ value = value.substring(1).trim();
3288
+ switch (value) {
3289
+ case "NaN":
3290
+ case "Infinity":
3291
+ case "-Infinity":
3292
+ return 1 /* Literal */;
3293
+ case "null":
3294
+ case "false":
3295
+ case "undefined":
3296
+ return void 0;
3297
+ case "true":
3298
+ return 0 /* True */;
3299
+ }
3300
+ if (
3301
+ // double quote string
3302
+ /^"(?:[^"\\]+|\\.)*"$/.test(value) || // single quote string
3303
+ /^'(?:[^'\\]+|\\.)*'$/.test(value) || // template literal without any interpolations
3304
+ /^`(?:[^`\\$]+|\\.|\$(?!\{))*`$/.test(value)
3305
+ ) {
3306
+ return 2 /* QuotedString */;
3307
+ } else if (
3308
+ // octal literal
3309
+ /^-?0[oO]?[0-7](?:_?[0-7]+)*n?$/.test(value) || // hex literal
3310
+ /^-?0[xX][0-9a-fA-F](?:_?[0-9a-fA-F]+)*n?$/.test(value) || // binary literal
3311
+ /^-?0[bB][01](?:_?[01]+)*n?$/.test(value) || // integer or float
3312
+ /^-?\d(?:_?\d+)*(?:[.eE]\d(?:_?\d+)*|n?|\.?)$/.test(value)
3313
+ ) {
3314
+ return 1 /* Literal */;
3315
+ }
3316
+ return 3 /* Dynamic */;
3317
+ }
3318
+
3319
+ // src/extractors/html/index.ts
3320
+ function extractHTML(parsed) {
3321
+ return new HTMLExtractor(parsed).end();
3322
+ }
3323
+ var HTMLExtractor = class {
3324
+ #extractor;
3325
+ #read;
3326
+ #nodeDetails;
3327
+ #nodeIdCounter;
3328
+ #dynamicAttrValueCounter;
3329
+ constructor(parsed) {
3330
+ this.#extractor = new Extractor(parsed);
3331
+ this.#read = parsed.read.bind(parsed);
3332
+ this.#nodeDetails = {};
3333
+ this.#nodeIdCounter = 0;
3334
+ this.#dynamicAttrValueCounter = 0;
3335
+ parsed.program.body.forEach((node) => this.#visitNode(node));
3336
+ }
3337
+ end() {
3338
+ return { extracted: this.#extractor.end(), nodeDetails: this.#nodeDetails };
3339
+ }
3340
+ #visitNode(node) {
3341
+ var _a;
3342
+ let hasDynamicBody = false, hasDynamicAttrs = false, isDynamic = false;
3343
+ switch (node.type) {
3344
+ case 16 /* AttrTag */:
3345
+ (_a = node.body) == null ? void 0 : _a.forEach((child) => {
3346
+ if (this.#visitNode(child))
3347
+ hasDynamicBody = true;
3348
+ });
3349
+ break;
3350
+ case 1 /* Tag */: {
3351
+ const nodeId = `${this.#nodeIdCounter++}`;
3352
+ ({ isDynamic, hasDynamicAttrs, hasDynamicBody } = this.#writeTag(
3353
+ node,
3354
+ nodeId
3355
+ ));
3356
+ this.#nodeDetails[nodeId] = { hasDynamicAttrs, hasDynamicBody };
3357
+ break;
3358
+ }
3359
+ case 17 /* Text */:
3360
+ this.#extractor.copy(node);
3361
+ break;
3362
+ case 22 /* Placeholder */:
3363
+ isDynamic = this.#read({
3364
+ start: node.start + 1,
3365
+ end: node.start + 2
3366
+ }) === "!";
3367
+ }
3368
+ return isDynamic || hasDynamicBody;
3369
+ }
3370
+ #writeTag(node, id) {
3371
+ const isDynamic = !node.nameText || !isHTMLTag(node.nameText);
3372
+ let hasDynamicAttrs = false, hasDynamicBody = false;
3373
+ if (!isDynamic) {
3374
+ ({ hasDynamicAttrs, hasDynamicBody } = this.#writeHTMLTag(node, id));
3375
+ } else {
3376
+ this.#writeCustomTag(node);
3377
+ }
3378
+ return { isDynamic, hasDynamicAttrs, hasDynamicBody };
3379
+ }
3380
+ #writeHTMLTag(node, id) {
3381
+ var _a, _b;
3382
+ let hasDynamicAttrs = false, hasDynamicBody = false;
3383
+ this.#extractor.write("<");
3384
+ this.#extractor.copy(node.name);
3385
+ this.#extractor.write(` data-marko-node-id="${id}"`);
3386
+ (_a = node.attrs) == null ? void 0 : _a.forEach((attr) => {
3387
+ if (attr.type === 10 /* AttrNamed */)
3388
+ this.#writeAttrNamed(attr);
3389
+ else if (attr.type === 15 /* AttrSpread */)
3390
+ hasDynamicAttrs = true;
3391
+ });
3392
+ this.#extractor.write(">");
3393
+ (_b = node.body) == null ? void 0 : _b.forEach((child) => {
3394
+ if (this.#visitNode(child))
3395
+ hasDynamicBody = true;
3396
+ });
3397
+ this.#extractor.write(`</${node.nameText}>`);
3398
+ return { hasDynamicAttrs, hasDynamicBody };
3399
+ }
3400
+ #writeCustomTag(node) {
3401
+ if (node.body) {
3402
+ this.#extractor.write("<div>");
3403
+ node.body.forEach((node2) => this.#visitNode(node2));
3404
+ this.#extractor.write("</div>");
3405
+ }
3406
+ }
3407
+ #writeAttrNamed(attr) {
3408
+ this.#extractor.write(" ");
3409
+ this.#extractor.copy(attr.name);
3410
+ if (attr.value === void 0 || attr.name.start === attr.name.end || attr.value.type === 14 /* AttrMethod */) {
3411
+ return;
3412
+ }
3413
+ const valueString = this.#read(attr.value);
3414
+ const valueType = getAttributeValueType(valueString);
3415
+ if (valueType === void 0)
3416
+ return;
3417
+ switch (valueType) {
3418
+ case 0 /* True */:
3419
+ break;
3420
+ case 1 /* Literal */:
3421
+ this.#extractor.write('="');
3422
+ this.#extractor.copy({
3423
+ start: attr.value.start + valueString.search(/[^=\s]/g),
3424
+ end: attr.value.end
3425
+ });
3426
+ this.#extractor.write('"');
3427
+ break;
3428
+ case 2 /* QuotedString */:
3429
+ this.#extractor.write('="');
3430
+ this.#extractor.copy({
3431
+ start: attr.value.start + valueString.search(/[^=\s]/g) + 1,
3432
+ end: attr.value.end - 1
3433
+ });
3434
+ this.#extractor.write('"');
3435
+ break;
3436
+ case 3 /* Dynamic */:
3437
+ this.#extractor.write(`="dynamic${this.#dynamicAttrValueCounter++}"`);
3438
+ break;
3439
+ }
3440
+ }
3441
+ };
3291
3442
  export {
3292
3443
  NodeType,
3293
3444
  processors_exports as Processors,
3294
3445
  project_exports as Project,
3295
3446
  ScriptLang,
3296
3447
  UNFINISHED,
3448
+ extractHTML,
3297
3449
  extractScript,
3298
3450
  extractStyle,
3299
3451
  getExt,
@@ -1,11 +1,12 @@
1
1
  /// <reference types="node" />
2
2
  import type TS from "typescript/lib/tsserverlibrary";
3
3
  import type { TaglibLookup } from "@marko/babel-utils";
4
- import * as defaultCompiler from "@marko/compiler";
4
+ import type * as Compiler from "@marko/compiler";
5
5
  import { ScriptLang } from "../extractors/script";
6
6
  export interface Meta {
7
- compiler: typeof defaultCompiler;
8
- config: Omit<defaultCompiler.Config, "cache" | "translator"> & {
7
+ fallback: boolean;
8
+ compiler: typeof Compiler;
9
+ config: Omit<Compiler.Config, "cache" | "translator"> & {
9
10
  cache: Map<any, any>;
10
11
  translator: {
11
12
  runtimeTypes?: string;
@@ -21,7 +22,7 @@ interface TypeLibs {
21
22
  markoTypesCode: string | undefined;
22
23
  }
23
24
  declare const defaultTypeLibs: Partial<TypeLibs>;
24
- export declare function getCompiler(dir?: string): typeof defaultCompiler;
25
+ export declare function getCompiler(dir?: string): typeof Compiler;
25
26
  export declare function getCache(dir?: string): Map<any, any>;
26
27
  export declare function getConfig(dir?: string): Omit<{
27
28
  output?: "source" | "html" | "dom" | "hydrate" | "migrate" | undefined;
package/package.json CHANGED
@@ -1,23 +1,25 @@
1
1
  {
2
2
  "name": "@marko/language-tools",
3
3
  "description": "Marko Language Tools",
4
- "version": "2.0.11",
4
+ "version": "2.1.1",
5
5
  "bugs": "https://github.com/marko-js/language-server/issues/new?template=Bug_report.md",
6
+ "peerDependencies": {
7
+ "@marko/compiler": "^5.28.4"
8
+ },
6
9
  "dependencies": {
7
10
  "@babel/helper-validator-identifier": "^7.22.5",
8
- "@babel/parser": "^7.22.5",
9
- "@marko/compiler": "5.28.4",
10
- "@marko/translator-default": "5.26.5",
11
+ "@babel/parser": "^7.22.7",
11
12
  "htmljs-parser": "^5.5.0",
12
13
  "relative-import-path": "^1.0.0"
13
14
  },
14
15
  "devDependencies": {
15
16
  "@babel/code-frame": "^7.22.5",
16
- "@marko/compiler": "^5.28.5",
17
+ "@marko/compiler": "^5.31.1",
18
+ "@marko/translator-default": "^5.29.1",
17
19
  "@types/babel__code-frame": "^7.0.3",
18
20
  "@types/babel__helper-validator-identifier": "^7.15.0",
19
21
  "@typescript/vfs": "^1.4.0",
20
- "marko": "^5.26.5",
22
+ "marko": "^5.29.1",
21
23
  "mitata": "^0.1.6",
22
24
  "tsx": "^3.12.7"
23
25
  },
@@ -51,8 +53,6 @@
51
53
  },
52
54
  "scripts": {
53
55
  "bench": "BENCH=1 mocha './src/**/__tests__/*.test.ts'",
54
- "build": "tsc -b && tsx build.mts",
55
- "test": "mocha './src/**/__tests__/*.test.ts'",
56
- "test:update": "mocha './src/**/__tests__/*.test.ts' --update"
56
+ "build": "tsc -b && tsx build.mts"
57
57
  }
58
58
  }