sec-edgar-api 1.0.6 → 1.0.8

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.
@@ -15,8 +15,8 @@ export interface XbrlFilingSummary {
15
15
  reportFormat: string;
16
16
  reports: XbrlFilingSummaryReport[];
17
17
  }
18
- type XbrlFilingSummaryMenuCategory = 'Cover' | 'Statements' | 'Notes' | 'Policies' | 'Tables' | 'Details';
19
- type XbrlFilingSummaryReportType = 'Sheet' | 'Notes' | 'Book';
18
+ export type XbrlFilingSummaryMenuCategory = 'Cover' | 'Statements' | 'Notes' | 'Policies' | 'Tables' | 'Details';
19
+ export type XbrlFilingSummaryReportType = 'Sheet' | 'Notes' | 'Book';
20
20
  export interface XbrlFilingSummaryReport {
21
21
  longName: string;
22
22
  shortName: string;
@@ -38,4 +38,3 @@ export default class FilingSummaryParser {
38
38
  private toText;
39
39
  parse(xml: string): XbrlFilingSummary | null;
40
40
  }
41
- export {};
@@ -30,7 +30,7 @@ export default class ReportRawBuilder {
30
30
  createFacts(companyFacts: CompanyFactListData, includeNamePrefix?: boolean): {
31
31
  facts: FactItem[];
32
32
  };
33
- private getFactKey;
33
+ getFactKey(fact: FactItem, pathSeparator: string): string;
34
34
  buildReports(params: BuildReportsParams): ReportRaw[];
35
35
  private createReportKey;
36
36
  private createReport;
@@ -0,0 +1,36 @@
1
+ import { DocumentXbrlResult } from '../services/DocumentParser/parsers/parse-xbrl';
2
+ import { XbrlFilingSummaryReport } from '../services/DocumentParser/XBRLParser/FilingSummaryParser';
3
+ export interface XbrlFilingSummaryReportWithTrees extends XbrlFilingSummaryReport {
4
+ calculationTree: TreeNode[];
5
+ presentationTree: TreeNode[];
6
+ }
7
+ export type MemberInclusionRule = 'always' | 'inReportsWherePresent' | 'never';
8
+ interface TreeNode {
9
+ label: string;
10
+ value: number | string | null;
11
+ unit: string;
12
+ period: number;
13
+ key: string;
14
+ isPeriodStart: boolean;
15
+ weight: number;
16
+ members?: MemberFact[];
17
+ children?: TreeNode[];
18
+ }
19
+ interface MemberFact {
20
+ segments: {
21
+ dimension: string;
22
+ value: string;
23
+ }[];
24
+ value: string | number | null;
25
+ }
26
+ export interface BuildReportTreesParams {
27
+ xbrlJson: DocumentXbrlResult;
28
+ /**
29
+ * Where members should be included in the tree nodes.
30
+ *
31
+ * @default 'inReportsWherePresent'
32
+ */
33
+ memberInclusionRule?: MemberInclusionRule;
34
+ }
35
+ export declare function buildReportTrees(params: BuildReportTreesParams): XbrlFilingSummaryReportWithTrees[];
36
+ export {};
@@ -0,0 +1,209 @@
1
+ "use strict";
2
+ var __assign = (this && this.__assign) || function () {
3
+ __assign = Object.assign || function(t) {
4
+ for (var s, i = 1, n = arguments.length; i < n; i++) {
5
+ s = arguments[i];
6
+ for (var p in s) if (Object.prototype.hasOwnProperty.call(s, p))
7
+ t[p] = s[p];
8
+ }
9
+ return t;
10
+ };
11
+ return __assign.apply(this, arguments);
12
+ };
13
+ Object.defineProperty(exports, "__esModule", { value: true });
14
+ exports.buildReportTrees = void 0;
15
+ function hrefToKey(href) {
16
+ var fragment = href.split('#').pop() || '';
17
+ return fragment.replace('_', ':');
18
+ }
19
+ function getLabelTypeByHref(linkbase) {
20
+ var _a, _b, _c, _d;
21
+ var labelLink = (_a = linkbase === null || linkbase === void 0 ? void 0 : linkbase.labelLink) === null || _a === void 0 ? void 0 : _a[0];
22
+ var labelLocByHref = new Map((_b = labelLink === null || labelLink === void 0 ? void 0 : labelLink.loc) === null || _b === void 0 ? void 0 : _b.map(function (l) { return [l.href, l]; }));
23
+ var labelArcByFrom = new Map((_c = labelLink === null || labelLink === void 0 ? void 0 : labelLink.labelArc) === null || _c === void 0 ? void 0 : _c.map(function (l) { return [l.from, l]; }));
24
+ var labelByTypeByLabelId = new Map();
25
+ (_d = labelLink === null || labelLink === void 0 ? void 0 : labelLink.label) === null || _d === void 0 ? void 0 : _d.forEach(function (l) {
26
+ var _a;
27
+ var bucket = (_a = labelByTypeByLabelId.get(l.label)) !== null && _a !== void 0 ? _a : labelByTypeByLabelId.set(l.label, {}).get(l.label);
28
+ bucket[l.type.substring(l.type.lastIndexOf('/') + 1)] = l.text;
29
+ });
30
+ var labelByTypeByHref = new Map();
31
+ labelLocByHref.forEach(function (locator, href) {
32
+ var _a, _b, _c;
33
+ labelByTypeByHref.set(href, (_c = labelByTypeByLabelId.get((_b = (_a = labelArcByFrom.get(locator.label)) === null || _a === void 0 ? void 0 : _a.to) !== null && _b !== void 0 ? _b : '')) !== null && _c !== void 0 ? _c : {});
34
+ });
35
+ return labelByTypeByHref;
36
+ }
37
+ function getBestLabel(params) {
38
+ var _a;
39
+ var href = params.href, labelByHref = params.labelByHref, preferredLabel = params.preferredLabel;
40
+ var bucket = labelByHref.get(href);
41
+ if (!bucket)
42
+ return null;
43
+ // try getting preferred label
44
+ var preferredLabelType = preferredLabel === null || preferredLabel === void 0 ? void 0 : preferredLabel.substring((preferredLabel === null || preferredLabel === void 0 ? void 0 : preferredLabel.lastIndexOf('/')) + 1);
45
+ if (preferredLabelType && bucket[preferredLabelType])
46
+ return bucket[preferredLabelType];
47
+ // if not provided, choose first of these.
48
+ for (var _i = 0, _b = ['verboseLabel', 'terseLabel', 'label', 'periodEndLabel']; _i < _b.length; _i++) {
49
+ var type = _b[_i];
50
+ if (bucket[type])
51
+ return bucket[type];
52
+ }
53
+ // return whatever is left
54
+ return (_a = Object.values(bucket)[0]) !== null && _a !== void 0 ? _a : null;
55
+ }
56
+ function getPeriodFacts(params) {
57
+ var _a;
58
+ var factsByConcept = params.factsByConcept, conceptKey = params.conceptKey, isPeriodStart = params.isPeriodStart;
59
+ var facts = (_a = factsByConcept.get(conceptKey)) !== null && _a !== void 0 ? _a : [];
60
+ var primaryFacts = facts.filter(function (f) { return f.isCurrentPeriod; });
61
+ if (!isPeriodStart || primaryFacts.length === 0)
62
+ return primaryFacts;
63
+ var primaryFact = primaryFacts[0];
64
+ var maxEnd = facts.reduce(function (max, f) { return (f.end > max && f.end < primaryFact.end ? f.end : max); }, '0000-00-00');
65
+ return facts.filter(function (f) { return !f.isCurrentPeriod && f.end === maxEnd; });
66
+ }
67
+ function extractMemberFacts(facts, memberInclusionRule, allowedMembers) {
68
+ if (memberInclusionRule === 'never')
69
+ return [];
70
+ var allMembers = facts
71
+ .filter(function (f) { var _a, _b; return ((_b = (_a = f.segments) === null || _a === void 0 ? void 0 : _a.length) !== null && _b !== void 0 ? _b : 0) > 0; })
72
+ .map(function (f) { return ({ value: f.value, segments: f.segments }); });
73
+ if (memberInclusionRule === 'always')
74
+ return allMembers;
75
+ return allMembers.filter(function (m) {
76
+ return m.segments.every(function (s) { return (allowedMembers === null || allowedMembers === void 0 ? void 0 : allowedMembers.has(s.value)) && (allowedMembers === null || allowedMembers === void 0 ? void 0 : allowedMembers.has(s.dimension)); });
77
+ });
78
+ }
79
+ function extractPrimaryFact(facts) {
80
+ var _a;
81
+ return (_a = facts.find(function (f) { var _a, _b; return !((_b = (_a = f.segments) === null || _a === void 0 ? void 0 : _a.length) !== null && _b !== void 0 ? _b : 0); })) !== null && _a !== void 0 ? _a : null;
82
+ }
83
+ function buildTemplateHierarchyFlat(params) {
84
+ var _a, _b, _c, _d, _e, _f, _g, _h, _j, _k, _l, _m;
85
+ var arcs = params.arcs, labelByHref = params.labelByHref, locByLabel = params.locByLabel, factsByConcept = params.factsByConcept, allowedMembers = params.allowedMembers, _o = params.memberInclusionRule, memberInclusionRule = _o === void 0 ? 'inReportsWherePresent' : _o;
86
+ var itemsById = new Map();
87
+ for (var _i = 0, arcs_1 = arcs; _i < arcs_1.length; _i++) {
88
+ var arc = arcs_1[_i];
89
+ var hrefFrom = (_b = (_a = locByLabel.get(arc.from)) === null || _a === void 0 ? void 0 : _a.href) !== null && _b !== void 0 ? _b : '';
90
+ var hrefTo = (_d = (_c = locByLabel.get(arc.to)) === null || _c === void 0 ? void 0 : _c.href) !== null && _d !== void 0 ? _d : '';
91
+ var keyFrom = hrefToKey(hrefFrom);
92
+ var keyTo = hrefToKey(hrefTo);
93
+ var isPeriodStart = (_f = (_e = arc.preferredLabel) === null || _e === void 0 ? void 0 : _e.endsWith('periodStartLabel')) !== null && _f !== void 0 ? _f : false;
94
+ if (!itemsById.has(arc.from)) {
95
+ var periodFactsFrom = getPeriodFacts({ conceptKey: keyFrom, factsByConcept: factsByConcept, isPeriodStart: isPeriodStart });
96
+ var membersFrom = extractMemberFacts(periodFactsFrom, memberInclusionRule, allowedMembers);
97
+ var primaryFactFrom = extractPrimaryFact(periodFactsFrom);
98
+ itemsById.set(arc.from, {
99
+ id: arc.from,
100
+ parentId: null,
101
+ key: keyFrom,
102
+ parentKey: null,
103
+ weight: 1,
104
+ order: 0,
105
+ label: (_g = getBestLabel({ href: hrefFrom, labelByHref: labelByHref, preferredLabel: arc.preferredLabel })) !== null && _g !== void 0 ? _g : keyFrom,
106
+ isPeriodStart: isPeriodStart,
107
+ period: (primaryFactFrom === null || primaryFactFrom === void 0 ? void 0 : primaryFactFrom.period) || 0,
108
+ value: (_h = primaryFactFrom === null || primaryFactFrom === void 0 ? void 0 : primaryFactFrom.value) !== null && _h !== void 0 ? _h : null,
109
+ unit: (_j = primaryFactFrom === null || primaryFactFrom === void 0 ? void 0 : primaryFactFrom.unit) !== null && _j !== void 0 ? _j : '',
110
+ members: membersFrom,
111
+ children: [],
112
+ });
113
+ }
114
+ var periodFactsTo = getPeriodFacts({ conceptKey: keyTo, factsByConcept: factsByConcept, isPeriodStart: isPeriodStart });
115
+ var membersTo = extractMemberFacts(periodFactsTo, memberInclusionRule, allowedMembers);
116
+ var primaryFactTo = extractPrimaryFact(periodFactsTo);
117
+ var hierarchyTo = {
118
+ id: arc.to,
119
+ parentId: arc.from,
120
+ key: keyTo,
121
+ parentKey: arc.from ? hrefToKey(hrefFrom) : null,
122
+ weight: arc.weight || 1,
123
+ order: arc.order || 0,
124
+ label: (_k = getBestLabel({ href: hrefTo, labelByHref: labelByHref, preferredLabel: arc.preferredLabel })) !== null && _k !== void 0 ? _k : keyTo,
125
+ isPeriodStart: isPeriodStart,
126
+ period: (primaryFactTo === null || primaryFactTo === void 0 ? void 0 : primaryFactTo.period) || 0,
127
+ value: (_l = primaryFactTo === null || primaryFactTo === void 0 ? void 0 : primaryFactTo.value) !== null && _l !== void 0 ? _l : null,
128
+ unit: (_m = primaryFactTo === null || primaryFactTo === void 0 ? void 0 : primaryFactTo.unit) !== null && _m !== void 0 ? _m : '',
129
+ members: membersTo,
130
+ children: [],
131
+ };
132
+ if (!itemsById.has(arc.to)) {
133
+ itemsById.set(arc.to, hierarchyTo);
134
+ }
135
+ else {
136
+ Object.assign(itemsById.get(arc.to), hierarchyTo);
137
+ }
138
+ itemsById.get(arc.from).children.push(itemsById.get(arc.to));
139
+ }
140
+ return itemsById;
141
+ }
142
+ function hierarchyToTree(itemsById) {
143
+ itemsById.forEach(function (item) {
144
+ var _a, _b;
145
+ if (item.parentId) {
146
+ itemsById.delete(item.id);
147
+ }
148
+ // eslint-disable-next-line @typescript-eslint/no-explicit-any
149
+ var itemUntyped = item;
150
+ delete itemUntyped.id;
151
+ delete itemUntyped.parentId;
152
+ delete itemUntyped.parentKey;
153
+ delete itemUntyped.order;
154
+ if (((_a = itemUntyped.children) === null || _a === void 0 ? void 0 : _a.length) === 0)
155
+ delete itemUntyped.children;
156
+ if (((_b = itemUntyped.members) === null || _b === void 0 ? void 0 : _b.length) === 0)
157
+ delete itemUntyped.members;
158
+ });
159
+ return Array.from(itemsById.values());
160
+ }
161
+ function buildReportTrees(params) {
162
+ var _a, _b, _c, _d, _e, _f, _g;
163
+ var xbrlJson = params.xbrlJson, _h = params.memberInclusionRule, memberInclusionRule = _h === void 0 ? 'inReportsWherePresent' : _h;
164
+ var filingSummary = xbrlJson.filingSummary;
165
+ if (!filingSummary)
166
+ return [];
167
+ var labelByHref = getLabelTypeByHref((_a = xbrlJson.linkbaseLabel) === null || _a === void 0 ? void 0 : _a.xbrl);
168
+ var factsByConcept = new Map();
169
+ xbrlJson.facts.forEach(function (fact) {
170
+ var _a;
171
+ var bucket = (_a = factsByConcept.get(fact.name)) !== null && _a !== void 0 ? _a : factsByConcept.set(fact.name, []).get(fact.name);
172
+ bucket.push(fact);
173
+ });
174
+ var calculationLinks = (_d = (_c = (_b = xbrlJson.linkbaseCalculation) === null || _b === void 0 ? void 0 : _b.xbrl) === null || _c === void 0 ? void 0 : _c.calculationLink) !== null && _d !== void 0 ? _d : [];
175
+ var presentationLinks = (_g = (_f = (_e = xbrlJson.linkbasePresentation) === null || _e === void 0 ? void 0 : _e.xbrl) === null || _f === void 0 ? void 0 : _f.presentationLink) !== null && _g !== void 0 ? _g : [];
176
+ // Iterate through the xbrl reports and build tree structures
177
+ var reports = filingSummary.reports.map(function (report) {
178
+ var _a, _b, _c, _d, _e;
179
+ var calculationLink = calculationLinks.find(function (link) { return link.role === report.role; });
180
+ var presentationLink = presentationLinks.find(function (link) { return link.role === report.role; });
181
+ var locatorByLabelCalc = new Map((_b = (_a = calculationLink === null || calculationLink === void 0 ? void 0 : calculationLink.loc) === null || _a === void 0 ? void 0 : _a.map(function (l) { return [l.label, l]; })) !== null && _b !== void 0 ? _b : []);
182
+ var locatorByLabelPres = new Map((_d = (_c = presentationLink === null || presentationLink === void 0 ? void 0 : presentationLink.loc) === null || _c === void 0 ? void 0 : _c.map(function (l) { return [l.label, l]; })) !== null && _d !== void 0 ? _d : []);
183
+ var allowedMembers = new Set();
184
+ (_e = presentationLink === null || presentationLink === void 0 ? void 0 : presentationLink.presentationArc) === null || _e === void 0 ? void 0 : _e.forEach(function (arc) {
185
+ var _a, _b, _c, _d;
186
+ allowedMembers.add(hrefToKey((_b = (_a = locatorByLabelPres.get(arc.to)) === null || _a === void 0 ? void 0 : _a.href) !== null && _b !== void 0 ? _b : ''));
187
+ allowedMembers.add(hrefToKey((_d = (_c = locatorByLabelPres.get(arc.from)) === null || _c === void 0 ? void 0 : _c.href) !== null && _d !== void 0 ? _d : ''));
188
+ });
189
+ var hierarchyCalc = buildTemplateHierarchyFlat({
190
+ arcs: (calculationLink === null || calculationLink === void 0 ? void 0 : calculationLink.calculationArc) || [],
191
+ labelByHref: labelByHref,
192
+ locByLabel: locatorByLabelCalc,
193
+ factsByConcept: factsByConcept,
194
+ allowedMembers: allowedMembers,
195
+ memberInclusionRule: memberInclusionRule,
196
+ });
197
+ var hierarchyPres = buildTemplateHierarchyFlat({
198
+ arcs: (presentationLink === null || presentationLink === void 0 ? void 0 : presentationLink.presentationArc) || [],
199
+ labelByHref: labelByHref,
200
+ locByLabel: locatorByLabelPres,
201
+ factsByConcept: factsByConcept,
202
+ allowedMembers: allowedMembers,
203
+ memberInclusionRule: memberInclusionRule,
204
+ });
205
+ return __assign(__assign({}, report), { calculationTree: hierarchyToTree(hierarchyCalc), presentationTree: hierarchyToTree(hierarchyPres) });
206
+ });
207
+ return reports;
208
+ }
209
+ exports.buildReportTrees = buildReportTrees;
@@ -1,4 +1,17 @@
1
1
  import { XbrlLinkbase } from '../types/xbrl.type';
2
+ export declare function getLabelsByTypeByTaxonomy(labelLinkbase: XbrlLinkbase): Record<string, Record<string, string>>;
3
+ /**
4
+ * The primary label based on priority: verboseLabel > terseLabel > label > periodEndLabel > first available label (excluding periodStartLabel)
5
+ *
6
+ * @param labelsByType The result of getLabelsByTypeByTaxonomy[key]
7
+ */
8
+ export declare function getPrimaryLabel(labelsByType: Record<string, string>): string;
9
+ /**
10
+ * The primary documentation based on priority: documentation > longest available label
11
+ *
12
+ * @param labelsByType The result of getLabelsByTypeByTaxonomy[key]
13
+ */
14
+ export declare function getPrimaryDocumentation(labelsByType: Record<string, string>): string;
2
15
  /**
3
16
  * Gets labels by taxonomy from the label linkbase. priority level: verboseLabel > terseLabel > label.
4
17
  */
@@ -1,37 +1,61 @@
1
1
  "use strict";
2
2
  Object.defineProperty(exports, "__esModule", { value: true });
3
- exports.getTaxonomyFromId = exports.getLabelByTaxonomy = void 0;
4
- /**
5
- * Gets labels by taxonomy from the label linkbase. priority level: verboseLabel > terseLabel > label.
6
- */
7
- function getLabelByTaxonomy(labelLinkbase) {
3
+ exports.getTaxonomyFromId = exports.getLabelByTaxonomy = exports.getPrimaryDocumentation = exports.getPrimaryLabel = exports.getLabelsByTypeByTaxonomy = void 0;
4
+ function getLabelsByTypeByTaxonomy(labelLinkbase) {
8
5
  var _a;
9
- var labelByTaxonomy = {};
10
- var taxonomyWithVerboseLabels = new Set();
11
- (_a = labelLinkbase.labelLink) === null || _a === void 0 ? void 0 : _a.forEach(function (link) {
6
+ var labelsByTypeByTaxonomy = {};
7
+ (_a = labelLinkbase === null || labelLinkbase === void 0 ? void 0 : labelLinkbase.labelLink) === null || _a === void 0 ? void 0 : _a.forEach(function (link) {
12
8
  var _a;
13
9
  (_a = link.label) === null || _a === void 0 ? void 0 : _a.forEach(function (_a) {
14
- var _b = _a.label, label = _b === void 0 ? '' : _b, _c = _a.text, text = _c === void 0 ? '' : _c, _d = _a.role, role = _d === void 0 ? '' : _d;
10
+ var _b;
11
+ var _c = _a.label, label = _c === void 0 ? '' : _c, _d = _a.text, text = _d === void 0 ? '' : _d, _e = _a.role, role = _e === void 0 ? '' : _e;
15
12
  var taxonomy = getTaxonomyFromId(label);
16
- // skip if verbose label already exists for this taxonomy
17
- if (taxonomyWithVerboseLabels.has(taxonomy)) {
18
- return;
19
- }
20
- // label, terseLabel, or verboseLabel
21
13
  var labelType = role.substring(role.lastIndexOf('/') + 1);
22
- // skip periodStartLabel. Used for beginning cash position, but overwrites end cash position.
23
- if (labelType === 'periodStartLabel') {
24
- return;
25
- }
26
- if (labelType === 'verboseLabel') {
27
- taxonomyWithVerboseLabels.add(taxonomy);
28
- }
29
- // prefer terseLabel over regular label
30
- if (!labelByTaxonomy[taxonomy] || labelType === 'terseLabel' || labelType === 'verboseLabel') {
31
- labelByTaxonomy[taxonomy] = text;
32
- }
14
+ (_b = labelsByTypeByTaxonomy[taxonomy]) !== null && _b !== void 0 ? _b : (labelsByTypeByTaxonomy[taxonomy] = {});
15
+ labelsByTypeByTaxonomy[taxonomy][labelType] = text;
33
16
  });
34
17
  });
18
+ return labelsByTypeByTaxonomy;
19
+ }
20
+ exports.getLabelsByTypeByTaxonomy = getLabelsByTypeByTaxonomy;
21
+ /**
22
+ * The primary label based on priority: verboseLabel > terseLabel > label > periodEndLabel > first available label (excluding periodStartLabel)
23
+ *
24
+ * @param labelsByType The result of getLabelsByTypeByTaxonomy[key]
25
+ */
26
+ function getPrimaryLabel(labelsByType) {
27
+ var _a, _b;
28
+ var preferredLabel = labelsByType.verboseLabel || labelsByType.terseLabel || labelsByType.label || labelsByType.periodEndLabel;
29
+ if (preferredLabel)
30
+ return preferredLabel;
31
+ // return the first available label that is not periodStartLabel
32
+ return (_b = (_a = Object.entries(labelsByType).find(function (_a) {
33
+ var k = _a[0], v = _a[1];
34
+ return k !== 'periodStartLabel' && v.length > 0;
35
+ })) === null || _a === void 0 ? void 0 : _a[1]) !== null && _b !== void 0 ? _b : '';
36
+ }
37
+ exports.getPrimaryLabel = getPrimaryLabel;
38
+ /**
39
+ * The primary documentation based on priority: documentation > longest available label
40
+ *
41
+ * @param labelsByType The result of getLabelsByTypeByTaxonomy[key]
42
+ */
43
+ function getPrimaryDocumentation(labelsByType) {
44
+ if (labelsByType.documentation)
45
+ return labelsByType.documentation;
46
+ var validKeys = Object.keys(labelsByType).filter(function (key) { return key !== 'periodStartLabel'; });
47
+ return validKeys.reduce(function (acc, curr) { return (acc.length > curr.length ? acc : curr); }, '');
48
+ }
49
+ exports.getPrimaryDocumentation = getPrimaryDocumentation;
50
+ /**
51
+ * Gets labels by taxonomy from the label linkbase. priority level: verboseLabel > terseLabel > label.
52
+ */
53
+ function getLabelByTaxonomy(labelLinkbase) {
54
+ var labelByTaxonomy = {};
55
+ var labelsByTypeByTaxonomy = getLabelsByTypeByTaxonomy(labelLinkbase);
56
+ for (var taxonomy in labelsByTypeByTaxonomy) {
57
+ labelByTaxonomy[taxonomy] = getPrimaryLabel(labelsByTypeByTaxonomy[taxonomy]);
58
+ }
35
59
  return labelByTaxonomy;
36
60
  }
37
61
  exports.getLabelByTaxonomy = getLabelByTaxonomy;
@@ -51,6 +75,21 @@ function getTaxonomyFromId(id) {
51
75
  var isLabelIndicatorPosition3 = parts[2] === 'lbl';
52
76
  var isKnownPrefixPosition1 = knownPrefixes[parts[0]] === true;
53
77
  var isNameInPosition2 = parts.length <= 2 || isLabelIndicatorPosition3 || isKnownPrefixPosition1 || isPascaleCase(parts[1]);
54
- return isNameInPosition2 ? parts.slice(0, 2).join(':') : parts.slice(1, 3).join(':');
78
+ var result = isNameInPosition2 ? parts.slice(0, 2).join(':') : parts.slice(1, 3).join(':');
79
+ // this happens when the prefix is touching the concept name like "loc_us-gaapAssetsCurrent_lab".
80
+ // The symbol "GAN" has this issue.
81
+ if (result.startsWith('loc:')) {
82
+ var idWithoutLoc_1 = id.substring(4);
83
+ var knownPrefix = Object.keys(knownPrefixes).find(function (prefix) { return idWithoutLoc_1.startsWith(prefix); });
84
+ if (knownPrefix) {
85
+ return "".concat(knownPrefix, ":").concat(idWithoutLoc_1.substring(knownPrefix.length).split('_')[0]);
86
+ }
87
+ // custom taxonomy, assume the first capital letter followed by a lowercase is the concept name. ex: GANAssetsCurrentCustomConcept.match(/([A-Z][a-z]+)/)
88
+ var indexUpperFollowedByLower = idWithoutLoc_1.search(/[a-z]/) - 1;
89
+ var customPrefix = idWithoutLoc_1.substring(0, indexUpperFollowedByLower);
90
+ var conceptName = idWithoutLoc_1.substring(indexUpperFollowedByLower).split('_')[0];
91
+ return "".concat(customPrefix, ":").concat(conceptName.replace(/'|"/g, ''));
92
+ }
93
+ return result.replace(/'|"/g, '');
55
94
  }
56
95
  exports.getTaxonomyFromId = getTaxonomyFromId;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "sec-edgar-api",
3
- "version": "1.0.6",
3
+ "version": "1.0.8",
4
4
  "description": "Fetch and parse SEC earnings reports and other filings. Useful for financial analysis.",
5
5
  "main": "build/index.js",
6
6
  "author": "Andrew Evers (https://github.com/andyevers)",