2
0

ModuleFactory.cs 4.4 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103
  1. using Jint.Native;
  2. using Jint.Native.Json;
  3. namespace Jint.Runtime.Modules;
  4. /// <summary>
  5. /// Factory which creates a single runtime <see cref="Module"/> from a given source.
  6. /// </summary>
  7. public static class ModuleFactory
  8. {
  9. /// <summary>
  10. /// Creates a <see cref="Module"/> for the usage within the given <paramref name="engine"/>
  11. /// from the provided javascript <paramref name="code"/>.
  12. /// </summary>
  13. /// <remarks>
  14. /// The returned modules location (see <see cref="Module.Location"/>) points to
  15. /// <see cref="Uri.LocalPath"/> if <see cref="ResolvedSpecifier.Uri"/> is not null. If
  16. /// <see cref="ResolvedSpecifier.Uri"/> is null, the modules location source will be null as well.
  17. /// </remarks>
  18. /// <exception cref="ParseErrorException">Is thrown if the provided <paramref name="code"/> can not be parsed.</exception>
  19. /// <exception cref="JavaScriptException">Is thrown if an error occured when parsing <paramref name="code"/>.</exception>
  20. public static Module BuildSourceTextModule(Engine engine, ResolvedSpecifier resolved, string code, ModuleParsingOptions? parsingOptions = null)
  21. {
  22. var source = resolved.Uri?.LocalPath ?? resolved.Key;
  23. AstModule module;
  24. var parserOptions = (parsingOptions ?? ModuleParsingOptions.Default).GetParserOptions();
  25. var parser = new Parser(parserOptions);
  26. try
  27. {
  28. module = parser.ParseModule(code, source);
  29. }
  30. catch (ParseErrorException ex)
  31. {
  32. ExceptionHelper.ThrowSyntaxError(engine.Realm, $"Error while loading module: error in module '{source}': {ex.Error}");
  33. module = null;
  34. }
  35. catch (Exception)
  36. {
  37. ExceptionHelper.ThrowJavaScriptException(engine, $"Could not load module {source}", (SourceLocation) default);
  38. module = null;
  39. }
  40. return BuildSourceTextModule(engine, new Prepared<AstModule>(module, parserOptions));
  41. }
  42. /// <summary>
  43. /// Creates a <see cref="Module"/> for the usage within the given <paramref name="engine"/>
  44. /// from the parsed <paramref name="preparedModule"/>.
  45. /// </summary>
  46. /// <remarks>
  47. /// The returned modules location (see <see cref="Module.Location"/>) will be set
  48. /// to <see cref="SourceLocation.Source"/> of the <paramref name="preparedModule"/>.
  49. /// </remarks>
  50. public static Module BuildSourceTextModule(Engine engine, Prepared<AstModule> preparedModule)
  51. {
  52. if (!preparedModule.IsValid)
  53. {
  54. ExceptionHelper.ThrowInvalidPreparedModuleArgumentException(nameof(preparedModule));
  55. }
  56. return new SourceTextModule(engine, engine.Realm, preparedModule, preparedModule.Program!.Location.Source, async: false);
  57. }
  58. /// <summary>
  59. /// Creates a <see cref="Module"/> for the usage within the given <paramref name="engine"/> for the
  60. /// provided JSON module <paramref name="jsonString"/>.
  61. /// </summary>
  62. /// <remarks>
  63. /// The returned modules location (see <see cref="Module.Location"/>) points to
  64. /// <see cref="Uri.LocalPath"/> if <see cref="ResolvedSpecifier.Uri"/> is not null. If
  65. /// <see cref="ResolvedSpecifier.Uri"/> is null, the modules location source will be null as well.
  66. /// </remarks>
  67. /// <exception cref="JavaScriptException">Is thrown if an error occured when parsing <paramref name="jsonString"/>.</exception>
  68. public static Module BuildJsonModule(Engine engine, ResolvedSpecifier resolved, string jsonString)
  69. {
  70. var source = resolved.Uri?.LocalPath;
  71. JsValue module;
  72. try
  73. {
  74. module = new JsonParser(engine).Parse(jsonString);
  75. }
  76. catch (Exception)
  77. {
  78. ExceptionHelper.ThrowJavaScriptException(engine, $"Could not load module {source}", (SourceLocation) default);
  79. module = null;
  80. }
  81. return BuildJsonModule(engine, module, resolved.Uri?.LocalPath);
  82. }
  83. /// <summary>
  84. /// Creates a <see cref="Module"/> for the usage within the given <paramref name="engine"/>
  85. /// from the parsed JSON provided in <paramref name="parsedJson"/>.
  86. /// </summary>
  87. /// <remarks>
  88. /// The returned modules location (see <see cref="Module.Location"/>) will be set
  89. /// to <paramref name="location"/>.
  90. /// </remarks>
  91. public static Module BuildJsonModule(Engine engine, JsValue parsedJson, string? location)
  92. {
  93. return new SyntheticModule(engine, engine.Realm, parsedJson, location);
  94. }
  95. }