• Home
  • Features
  • Pricing
  • Docs
  • Announcements
  • Sign In

source-academy / js-slang / 13750610219

09 Mar 2025 05:01PM UTC coverage: 81.086% (-0.04%) from 81.126%
13750610219

Pull #1741

github

web-flow
Merge 561e360c2 into 6aad26cce
Pull Request #1741: Bump prettier, ace-builds, and misc clean up

3438 of 4606 branches covered (74.64%)

Branch coverage included in aggregate %.

66 of 89 new or added lines in 12 files covered. (74.16%)

9 existing lines in 4 files now uncovered.

10782 of 12931 relevant lines covered (83.38%)

143543.43 hits per line

Source File
Press 'n' to go to next uncovered line, 'b' for previous

75.0
/src/modules/errors.ts
1
import type es from 'estree'
2

3
import { UNKNOWN_LOCATION } from '../constants'
62✔
4
import { RuntimeSourceError } from '../errors/runtimeSourceError'
62✔
5
import { ErrorSeverity, ErrorType, Node, SourceError } from '../types'
62✔
6
import { nonAlphanumericCharEncoding } from './preprocessor/filePaths'
62✔
7

8
export class ModuleInternalError extends RuntimeSourceError {
62✔
9
  constructor(
NEW
10
    public moduleName: string,
×
NEW
11
    public error?: any,
×
12
    node?: Node
13
  ) {
UNCOV
14
    super(node)
×
15
  }
16

17
  public explain() {
18
    return `Error(s) occured when executing the module '${this.moduleName}'.`
×
19
  }
20

21
  public elaborate() {
22
    return 'You may need to contact with the author for this module to fix this error.'
×
23
  }
24
}
25

26
abstract class ImportError implements SourceError {
27
  public type: ErrorType.IMPORT
28
  public severity = ErrorSeverity.ERROR
59✔
29
  public get location() {
30
    return this.node?.loc ?? UNKNOWN_LOCATION
127✔
31
  }
32

33
  constructor(public node?: Node) {}
59✔
34

35
  public abstract explain(): string
36
  public abstract elaborate(): string
37
}
38

39
export class ModuleConnectionError extends ImportError {
62✔
40
  private static message: string = `Unable to get modules.`
62✔
41
  private static elaboration: string = `You should check your Internet connection, and ensure you have used the correct module path.`
62✔
42
  constructor(node?: Node) {
43
    super(node)
3✔
44
  }
45

46
  public explain() {
47
    return ModuleConnectionError.message
×
48
  }
49

50
  public elaborate() {
51
    return ModuleConnectionError.elaboration
×
52
  }
53
}
54

55
export class ModuleNotFoundError extends ImportError {
62✔
56
  constructor(
57
    public moduleName: string,
13✔
58
    node?: Node
59
  ) {
60
    super(node)
13✔
61
  }
62

63
  public explain() {
64
    return `Module '${this.moduleName}' not found.`
9✔
65
  }
66

67
  public elaborate() {
68
    return 'You should check your import declarations, and ensure that all are valid modules.'
3✔
69
  }
70
}
71

72
export class UndefinedNamespaceImportError extends ImportError {
62✔
73
  constructor(
74
    public readonly moduleName: string,
19✔
75
    node?:
76
      | Exclude<es.ModuleDeclaration, es.ExportDefaultDeclaration>
77
      | es.ImportDeclaration['specifiers'][number]
78
      | es.ExportSpecifier
79
  ) {
80
    super(node)
19✔
81
  }
82

83
  public explain(): string {
84
    return `'${this.moduleName}' does not export any symbols!`
×
85
  }
86

87
  public elaborate(): string {
88
    return "Check your imports and make sure what you're trying to import exists!"
×
89
  }
90
}
91

92
export class UndefinedImportError extends UndefinedNamespaceImportError {
62✔
93
  constructor(
94
    public readonly symbol: string,
16✔
95
    moduleName: string,
96
    node?: es.ImportDeclaration['specifiers'][number] | es.ExportSpecifier
97
  ) {
98
    super(moduleName, node)
16✔
99
  }
100

101
  public explain(): string {
102
    return `'${this.moduleName}' does not contain a definition for '${this.symbol}'`
×
103
  }
104
}
105

106
export class UndefinedDefaultImportError extends UndefinedImportError {
62✔
107
  constructor(
108
    moduleName: string,
109
    node?: es.ImportDeclaration['specifiers'][number] | es.ExportSpecifier
110
  ) {
111
    super('default', moduleName, node)
10✔
112
  }
113

114
  public explain(): string {
115
    return `'${this.moduleName}' does not have a default export!`
×
116
  }
117
}
118

119
export class CircularImportError extends ImportError {
62✔
120
  constructor(public filePathsInCycle: string[]) {
6✔
121
    super()
6✔
122
  }
123

124
  public explain() {
125
    // We need to reverse the file paths in the cycle so that the
126
    // semantics of "'/a.js' -> '/b.js'" is "'/a.js' imports '/b.js'".
127
    const formattedCycle = this.filePathsInCycle
4✔
128
      .map(filePath => `'${filePath}'`)
12✔
129
      .reverse()
130
      .join(' -> ')
131
    return `Circular import detected: ${formattedCycle}.`
4✔
132
  }
133

134
  public elaborate() {
135
    return 'Break the circular import cycle by removing imports from any of the offending files.'
2✔
136
  }
137
}
138

139
export abstract class InvalidFilePathError extends ImportError {
62✔
140
  constructor(public filePath: string) {
8✔
141
    super()
8✔
142
  }
143

144
  abstract explain(): string
145

146
  abstract elaborate(): string
147
}
148

149
export class IllegalCharInFilePathError extends InvalidFilePathError {
62✔
150
  public explain() {
151
    const validNonAlphanumericChars = Object.keys(nonAlphanumericCharEncoding)
4✔
152
      .map(char => `'${char}'`)
16✔
153
      .join(', ')
154
    return `File path '${this.filePath}' must only contain alphanumeric chars and/or ${validNonAlphanumericChars}.`
4✔
155
  }
156

157
  public elaborate() {
158
    return 'Rename the offending file path to only use valid chars.'
2✔
159
  }
160
}
161

162
export class ConsecutiveSlashesInFilePathError extends InvalidFilePathError {
62✔
163
  public explain() {
164
    return `File path '${this.filePath}' cannot contain consecutive slashes '//'.`
4✔
165
  }
166

167
  public elaborate() {
168
    return 'Remove consecutive slashes from the offending file path.'
2✔
169
  }
170
}
171

172
export class DuplicateImportNameError extends ImportError {
62✔
173
  public readonly locString: string
174

175
  public get location() {
176
    return this.nodes[0].loc ?? UNKNOWN_LOCATION
×
177
  }
178

179
  constructor(
180
    public readonly name: string,
10✔
181
    public readonly nodes: Node[]
10✔
182
  ) {
183
    super()
10✔
184

185
    this.locString = nodes
10✔
186
      .map(({ loc }) => {
187
        const { source, start } = loc ?? UNKNOWN_LOCATION
23!
188
        return `(${source ?? 'Unknown File'}:${start.line}:${start.column})`
23!
189
      })
190
      .join(', ')
191
  }
192

193
  public explain() {
194
    return `Source does not support different imports from Source modules being given the same name. The following are the offending imports: ${this.locString}`
×
195
  }
196

197
  public elaborate() {
198
    return `You cannot have different symbols across different files being given the same declared name, for example: \`import { foo as a } from 'one_module';\` and \`import { bar as a } from 'another_module';
×
199
    You also cannot have different symbols from the same module with the same declared name, for example: \`import { foo as a } from 'one_module';\` and \`import { bar as a } from 'one_module'; `
200
  }
201
}
STATUS · Troubleshooting · Open an Issue · Sales · Support · CAREERS · ENTERPRISE · START FREE · SCHEDULE DEMO
ANNOUNCEMENTS · TWITTER · TOS & SLA · Supported CI Services · What's a CI service? · Automated Testing

© 2025 Coveralls, Inc