diff --git a/README.md b/README.md index 4886b0197..0573ebfe1 100644 --- a/README.md +++ b/README.md @@ -22,6 +22,8 @@ --- +> 🚀 **We're hiring!** Join HyperFormula team as a **Senior Software Engineer**. [See the role and apply](https://handsontable.traffit.com/public/an/4b09e1395bf8ea42ef86db4c4657992c2f48673d). + HyperFormula is a headless spreadsheet built in TypeScript, serving as both a parser and evaluator of spreadsheet formulas. It can be integrated into your browser or utilized as a service with Node.js as your back-end technology. ## What HyperFormula can be used for? diff --git a/docs/.vuepress/components/HiringBanner.vue b/docs/.vuepress/components/HiringBanner.vue new file mode 100644 index 000000000..55207e6f5 --- /dev/null +++ b/docs/.vuepress/components/HiringBanner.vue @@ -0,0 +1,87 @@ + + + + + diff --git a/docs/.vuepress/config.js b/docs/.vuepress/config.js index 6e95cc8a9..eecf3aa24 100644 --- a/docs/.vuepress/config.js +++ b/docs/.vuepress/config.js @@ -11,6 +11,7 @@ const searchPattern = new RegExp('^/api', 'i'); module.exports = { title: 'HyperFormula (v' + HyperFormula.version + ')', description: 'HyperFormula is an open-source, high-performance calculation engine for spreadsheets and web applications.', + globalUIComponents: ['HiringBanner'], head: [ // Import HF (required for the examples) [ 'script', { src: 'https://cdn.jsdelivr.net/npm/hyperformula/dist/hyperformula.full.min.js' } ], @@ -40,7 +41,7 @@ module.exports = { new Sentry.Replay({ maskAllText: false, blockAllMedia: false, - }), + }), ], }); }; diff --git a/src/DependencyGraph/EmptyCellVertex.ts b/src/DependencyGraph/EmptyCellVertex.ts index 99bbfa766..7daccc72e 100644 --- a/src/DependencyGraph/EmptyCellVertex.ts +++ b/src/DependencyGraph/EmptyCellVertex.ts @@ -9,6 +9,8 @@ import {EmptyValue, EmptyValueType} from '../interpreter/InterpreterValue' * Represents singleton vertex bound to all empty cells */ export class EmptyCellVertex { + public _graphId?: number + constructor() {} /** diff --git a/src/DependencyGraph/FormulaVertex.ts b/src/DependencyGraph/FormulaVertex.ts index cf1c02161..a6c38b6b6 100644 --- a/src/DependencyGraph/FormulaVertex.ts +++ b/src/DependencyGraph/FormulaVertex.ts @@ -16,6 +16,8 @@ import {Ast} from '../parser' import {ColumnsSpan, RowsSpan} from '../Span' export abstract class FormulaVertex { + public _graphId?: number + protected constructor( protected formula: Ast, protected cellAddress: SimpleCellAddress, diff --git a/src/DependencyGraph/Graph.ts b/src/DependencyGraph/Graph.ts index 60c5f3487..4aceca92b 100644 --- a/src/DependencyGraph/Graph.ts +++ b/src/DependencyGraph/Graph.ts @@ -18,7 +18,7 @@ export type DependencyQuery = (vertex: Node) => [(SimpleCellAddress | Simp * Idea for performance improvement: * - use Set[] instead of NodeId[][] for edgesSparseArray */ -export class Graph { +export class Graph { /** * A sparse array. The value nodesSparseArray[n] exists if and only if node n is in the graph. * @private @@ -32,12 +32,6 @@ export class Graph { */ private edgesSparseArray: NodeId[][] = [] - /** - * A mapping from node to its id. The value nodesIds.get(node) exists if and only if node is in the graph. - * @private - */ - private nodesIds: Map = new Map() - /** * A ProcessableValue object. * @private @@ -78,7 +72,7 @@ export class Graph { * @param node - node to check */ public hasNode(node: Node): boolean { - return this.nodesIds.has(node) + return node._graphId !== undefined } /** @@ -137,7 +131,7 @@ export class Graph { * @param node - a node to be added */ public addNodeAndReturnId(node: Node): NodeId { - const idOfExistingNode = this.nodesIds.get(node) + const idOfExistingNode = node._graphId if (idOfExistingNode !== undefined) { return idOfExistingNode @@ -148,7 +142,7 @@ export class Graph { this.nodesSparseArray[newId] = node this.edgesSparseArray[newId] = [] - this.nodesIds.set(node, newId) + node._graphId = newId return newId } @@ -183,7 +177,7 @@ export class Graph { * Removes node from graph */ public removeNode(node: Node): [(SimpleCellAddress | SimpleCellRange), Node][] { - const id = this.getNodeId(node) + const id = node._graphId if (id === undefined) { throw this.missingNodeError(node) @@ -199,7 +193,7 @@ export class Graph { delete this.nodesSparseArray[id] delete this.edgesSparseArray[id] this.infiniteRangeIds.delete(id) - this.nodesIds.delete(node) + node._graphId = undefined return dependencies } @@ -368,14 +362,14 @@ export class Graph { * Returns the internal id of a node. */ public getNodeId(node: Node): NodeId | undefined { - return this.nodesIds.get(node) + return node._graphId } /** * */ private getNodeIdIfNotNumber(node: Node | NodeId): NodeId | undefined { - return typeof node === 'number' ? node : this.nodesIds.get(node) + return typeof node === 'number' ? node : node._graphId } /** diff --git a/src/DependencyGraph/ParsingErrorVertex.ts b/src/DependencyGraph/ParsingErrorVertex.ts index b8535869c..6e7b036c5 100644 --- a/src/DependencyGraph/ParsingErrorVertex.ts +++ b/src/DependencyGraph/ParsingErrorVertex.ts @@ -10,6 +10,8 @@ import {ParsingError} from '../parser/Ast' * Represents a cell that contains a parsing error. */ export class ParsingErrorVertex { + public _graphId?: number + /** * Constructor */ diff --git a/src/DependencyGraph/RangeVertex.ts b/src/DependencyGraph/RangeVertex.ts index b64e1187d..cd0ef5b00 100644 --- a/src/DependencyGraph/RangeVertex.ts +++ b/src/DependencyGraph/RangeVertex.ts @@ -16,6 +16,7 @@ export type CriterionCache = Map * Represents vertex bound to range */ export class RangeVertex { + public _graphId?: number public bruteForce: boolean /** Cache for associative aggregate functions. */ private functionCache: Map diff --git a/src/DependencyGraph/ValueCellVertex.ts b/src/DependencyGraph/ValueCellVertex.ts index 5e4d7e329..2c1d8c7f9 100644 --- a/src/DependencyGraph/ValueCellVertex.ts +++ b/src/DependencyGraph/ValueCellVertex.ts @@ -18,6 +18,8 @@ export interface RawAndParsedValue { * Represents vertex which keeps static cell value */ export class ValueCellVertex { + public _graphId?: number + /** Static cell value. */ constructor(private parsedValue: ValueCellVertexValue, private rawValue: RawCellContent) { }