@moxn/kb-migrate 0.4.31 → 0.4.33

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.
@@ -105,7 +105,9 @@ describe('convertOneNoteHtmlToSections', () => {
105
105
  const charts = result.sections[1];
106
106
  const imageBlock = charts.content.find((b) => b.blockType === 'image');
107
107
  expect(imageBlock).toBeDefined();
108
- if (imageBlock && imageBlock.blockType === 'image' && imageBlock.type === 'storage') {
108
+ if (imageBlock &&
109
+ imageBlock.blockType === 'image' &&
110
+ imageBlock.type === 'storage') {
109
111
  expect(imageBlock.key).toMatch(/kb\/onenote\/test\/abc-123\./);
110
112
  expect(imageBlock.mediaType).toBe('image/png');
111
113
  expect(imageBlock.alt).toBe('semis relative performance');
@@ -34,6 +34,8 @@ export declare class OneNoteApiClient {
34
34
  listPages(sectionId: string, options?: {
35
35
  modifiedAfter?: Date;
36
36
  modifiedBefore?: Date;
37
+ createdAfter?: Date;
38
+ createdBefore?: Date;
37
39
  }): Promise<OneNotePage[]>;
38
40
  getPage(pageId: string): Promise<OneNotePage>;
39
41
  /**
@@ -42,16 +42,26 @@ export class OneNoteApiClient {
42
42
  return this.paginate(`${this.baseUrl}/${this.userSlug}/onenote/sectionGroups/${encodeURIComponent(sectionGroupId)}/sections?$top=${DEFAULT_PAGE_SIZE}`);
43
43
  }
44
44
  async listPages(sectionId, options) {
45
- const select = '$select=id,title,lastModifiedDateTime,links';
45
+ // OneNote uses legacy datetime property names (`createdTime`, `lastModifiedTime`)
46
+ // not Graph's standard `*DateTime`. Selecting the wrong name returns HTTP 400.
47
+ const select = '$select=id,title,createdTime,lastModifiedTime,links';
46
48
  const filters = [];
47
49
  if (options?.modifiedAfter) {
48
- filters.push(`lastModifiedDateTime ge ${options.modifiedAfter.toISOString()}`);
50
+ filters.push(`lastModifiedTime ge ${options.modifiedAfter.toISOString()}`);
49
51
  }
50
52
  if (options?.modifiedBefore) {
51
- filters.push(`lastModifiedDateTime le ${options.modifiedBefore.toISOString()}`);
53
+ filters.push(`lastModifiedTime le ${options.modifiedBefore.toISOString()}`);
52
54
  }
53
- const filter = filters.length ? `&$filter=${encodeURIComponent(filters.join(' and '))}` : '';
54
- return this.paginate(`${this.baseUrl}/${this.userSlug}/onenote/sections/${encodeURIComponent(sectionId)}/pages?$top=${DEFAULT_PAGE_SIZE}${filter}${filter ? '' : ''}&${select.slice(1)}`);
55
+ if (options?.createdAfter) {
56
+ filters.push(`createdTime ge ${options.createdAfter.toISOString()}`);
57
+ }
58
+ if (options?.createdBefore) {
59
+ filters.push(`createdTime le ${options.createdBefore.toISOString()}`);
60
+ }
61
+ const filter = filters.length
62
+ ? `&$filter=${encodeURIComponent(filters.join(' and '))}`
63
+ : '';
64
+ return this.paginate(`${this.baseUrl}/${this.userSlug}/onenote/sections/${encodeURIComponent(sectionId)}/pages?$top=${DEFAULT_PAGE_SIZE}${filter}&${select.slice(1)}`);
55
65
  }
56
66
  async getPage(pageId) {
57
67
  return this.requestJson(`${this.baseUrl}/${this.userSlug}/onenote/pages/${encodeURIComponent(pageId)}`);
@@ -139,7 +149,7 @@ export class OneNoteApiClient {
139
149
  const errorBody = await response.text().catch(() => '');
140
150
  throw new Error(`Graph API ${response.status} on ${url}: ${errorBody.slice(0, 400)}`);
141
151
  }
142
- throw lastError ?? new Error(`Graph API request failed after ${MAX_RETRIES} retries`);
152
+ throw (lastError ?? new Error(`Graph API request failed after ${MAX_RETRIES} retries`));
143
153
  }
144
154
  }
145
155
  function sleep(ms) {
@@ -453,9 +453,7 @@ function extractInlineMarkdown(node, ctx) {
453
453
  function walkInline(node, refs, ctx) {
454
454
  const tag = node.tagName?.toUpperCase();
455
455
  const style = node.getAttribute('style') ?? '';
456
- const children = node.childNodes
457
- .map((c) => renderChild(c, refs, ctx))
458
- .join('');
456
+ const children = node.childNodes.map((c) => renderChild(c, refs, ctx)).join('');
459
457
  switch (tag) {
460
458
  case 'B':
461
459
  case 'STRONG':
@@ -593,10 +591,22 @@ function textBlock(text) {
593
591
  return { blockType: 'text', text };
594
592
  }
595
593
  function block(b) {
596
- return { blocks: [b], refs: [], mediaCount: 0, skippedItemCount: 0, skippedReasons: [] };
594
+ return {
595
+ blocks: [b],
596
+ refs: [],
597
+ mediaCount: 0,
598
+ skippedItemCount: 0,
599
+ skippedReasons: [],
600
+ };
597
601
  }
598
602
  function empty() {
599
- return { blocks: [], refs: [], mediaCount: 0, skippedItemCount: 0, skippedReasons: [] };
603
+ return {
604
+ blocks: [],
605
+ refs: [],
606
+ mediaCount: 0,
607
+ skippedItemCount: 0,
608
+ skippedReasons: [],
609
+ };
600
610
  }
601
611
  /**
602
612
  * Collapse consecutive text blocks with two newlines between; drop empties.
@@ -20,6 +20,8 @@ export interface DiscoverOptions {
20
20
  pathPrefix?: string;
21
21
  modifiedAfter?: Date;
22
22
  modifiedBefore?: Date;
23
+ createdAfter?: Date;
24
+ createdBefore?: Date;
23
25
  }
24
26
  /**
25
27
  * Normalize any human text into a ltree-safe slug segment.
@@ -92,6 +92,8 @@ async function walkSection(client, section, pathSegs, ctx, ancestorSelected, sel
92
92
  const pages = await client.listPages(section.id, {
93
93
  modifiedAfter: opts.modifiedAfter,
94
94
  modifiedBefore: opts.modifiedBefore,
95
+ createdAfter: opts.createdAfter,
96
+ createdBefore: opts.createdBefore,
95
97
  });
96
98
  const sectionSeg = slugifyPathSegment(section.displayName);
97
99
  for (const page of pages) {
@@ -113,12 +115,11 @@ function toDiscovered(page, section, segs, ctx) {
113
115
  sectionName: section.displayName,
114
116
  sectionGroups: ctx.sectionGroups,
115
117
  onenoteWebUrl: page.links?.oneNoteWebUrl?.href,
116
- createdDateTime: page.createdDateTime,
117
- lastModifiedDateTime: page.lastModifiedDateTime,
118
+ createdDateTime: page.createdTime,
119
+ lastModifiedDateTime: page.lastModifiedTime,
118
120
  createdByEmail: page.createdBy?.user?.email ?? page.createdBy?.user?.userPrincipalName,
119
121
  createdByDisplayName: page.createdBy?.user?.displayName,
120
- lastModifiedByEmail: page.lastModifiedBy?.user?.email ??
121
- page.lastModifiedBy?.user?.userPrincipalName,
122
+ lastModifiedByEmail: page.lastModifiedBy?.user?.email ?? page.lastModifiedBy?.user?.userPrincipalName,
122
123
  };
123
124
  }
124
125
  /**
@@ -19,8 +19,8 @@ export interface OneNoteNotebook {
19
19
  displayName: string;
20
20
  isDefault?: boolean;
21
21
  isShared?: boolean;
22
- createdDateTime?: string;
23
- lastModifiedDateTime?: string;
22
+ createdTime?: string;
23
+ lastModifiedTime?: string;
24
24
  createdBy?: GraphIdentity;
25
25
  lastModifiedBy?: GraphIdentity;
26
26
  links?: {
@@ -39,22 +39,22 @@ export interface OneNoteSectionGroup {
39
39
  parentNotebookId?: string;
40
40
  /** ID of parent section group (for nested groups) */
41
41
  parentSectionGroupId?: string;
42
- createdDateTime?: string;
43
- lastModifiedDateTime?: string;
42
+ createdTime?: string;
43
+ lastModifiedTime?: string;
44
44
  }
45
45
  export interface OneNoteSection {
46
46
  id: string;
47
47
  displayName: string;
48
48
  parentNotebookId?: string;
49
49
  parentSectionGroupId?: string;
50
- createdDateTime?: string;
51
- lastModifiedDateTime?: string;
50
+ createdTime?: string;
51
+ lastModifiedTime?: string;
52
52
  }
53
53
  export interface OneNotePage {
54
54
  id: string;
55
55
  title: string;
56
- createdDateTime?: string;
57
- lastModifiedDateTime?: string;
56
+ createdTime?: string;
57
+ lastModifiedTime?: string;
58
58
  contentUrl?: string;
59
59
  parentSection?: {
60
60
  id: string;
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@moxn/kb-migrate",
3
- "version": "0.4.31",
3
+ "version": "0.4.33",
4
4
  "description": "Migration tool for importing documents into Moxn Knowledge Base from local files, Notion, Google Docs, and more",
5
5
  "type": "module",
6
6
  "main": "dist/index.js",