Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
1 change: 1 addition & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,7 @@ The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
### Added

- Added a message after `npm i hyperformula` that points AI assistants to the SKILLS file. The message needs `--foreground-scripts` to be visible in npm, and pnpm 10 needs the `postinstall` script to be approved first. [#1829](https://github.com/handsontable/hyperformula/pull/1829)
- Added `DetailedCellError.hasMessage`, so a consumer can tell a cell error that never carried a message (e.g. a custom function that omitted one) apart from one with a deliberately empty message — both previously surfaced identically as `message: ''`. [#1547](https://github.com/handsontable/hyperformula/issues/1547)

### Changed

Expand Down
6 changes: 6 additions & 0 deletions docs/guide/custom-functions.md
Original file line number Diff line number Diff line change
Expand Up @@ -326,6 +326,12 @@ custom error messages. Put them to good use: let your users know what caused the
error and how to avoid it in the future.
:::

Every error the engine raises while evaluating a formula carries a message. A custom function's
`message` argument stays optional — if you omit it, a consumer reading the resulting
`DetailedCellError` sees `message` as an empty string, the same value HyperFormula uses
for "no message". To tell the two cases apart, check `hasMessage`: `true` means a
message was set (even if it's a deliberately empty string), `false` means none was.

### Test your function

To make sure your function works correctly, add unit tests. Use a JavaScript
Expand Down
13 changes: 13 additions & 0 deletions hyperformula/src/CellValue.ts
Original file line number Diff line number Diff line change
Expand Up @@ -12,13 +12,26 @@ export class DetailedCellError {
public readonly type: ErrorType
public readonly message: string

/**
* Whether the underlying error carried a message at all.
*
* `message` collapses "no message" and "an empty message" into `''`; this flag
* keeps them apart for consumers that need to know whether a cause was stated.
* Errors the engine raises while evaluating a formula always carry a message. A
* `false` here means nobody stated a cause: a custom function that did not supply
* one, or an error value a user typed straight into a cell, where the cause is the
* typing itself and `originFunction` says so.
*/
public readonly hasMessage: boolean

constructor(
error: CellError,
public readonly value: string,
public readonly address?: string,
) {
this.type = error.type
this.message = error.message ?? ''
this.hasMessage = error.message !== undefined
}

public toString(): string {
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -36,6 +36,7 @@ const IGNORED_IN_STRUCTURAL_COMPARE = {
address: undefined,
originFunction: undefined,
argumentIndex: undefined,
hasMessage: undefined,
propagated: undefined,
originAddress: undefined,
originAddressVersion: undefined,
Expand Down
Loading