@okrlinkhub/okrhub 0.1.0

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.
Files changed (148) hide show
  1. package/LICENSE +201 -0
  2. package/README.md +579 -0
  3. package/dist/client/_generated/_ignore.d.ts +1 -0
  4. package/dist/client/_generated/_ignore.d.ts.map +1 -0
  5. package/dist/client/_generated/_ignore.js +3 -0
  6. package/dist/client/_generated/_ignore.js.map +1 -0
  7. package/dist/client/index.d.ts +593 -0
  8. package/dist/client/index.d.ts.map +1 -0
  9. package/dist/client/index.js +704 -0
  10. package/dist/client/index.js.map +1 -0
  11. package/dist/component/_generated/api.d.ts +72 -0
  12. package/dist/component/_generated/api.d.ts.map +1 -0
  13. package/dist/component/_generated/api.js +31 -0
  14. package/dist/component/_generated/api.js.map +1 -0
  15. package/dist/component/_generated/component.d.ts +1986 -0
  16. package/dist/component/_generated/component.d.ts.map +1 -0
  17. package/dist/component/_generated/component.js +11 -0
  18. package/dist/component/_generated/component.js.map +1 -0
  19. package/dist/component/_generated/dataModel.d.ts +46 -0
  20. package/dist/component/_generated/dataModel.d.ts.map +1 -0
  21. package/dist/component/_generated/dataModel.js +11 -0
  22. package/dist/component/_generated/dataModel.js.map +1 -0
  23. package/dist/component/_generated/server.d.ts +121 -0
  24. package/dist/component/_generated/server.d.ts.map +1 -0
  25. package/dist/component/_generated/server.js +78 -0
  26. package/dist/component/_generated/server.js.map +1 -0
  27. package/dist/component/convex.config.d.ts +3 -0
  28. package/dist/component/convex.config.d.ts.map +1 -0
  29. package/dist/component/convex.config.js +3 -0
  30. package/dist/component/convex.config.js.map +1 -0
  31. package/dist/component/entities/batch.d.ts +121 -0
  32. package/dist/component/entities/batch.d.ts.map +1 -0
  33. package/dist/component/entities/batch.js +81 -0
  34. package/dist/component/entities/batch.js.map +1 -0
  35. package/dist/component/entities/index.d.ts +13 -0
  36. package/dist/component/entities/index.d.ts.map +1 -0
  37. package/dist/component/entities/index.js +22 -0
  38. package/dist/component/entities/index.js.map +1 -0
  39. package/dist/component/entities/indicatorForecasts.d.ts +61 -0
  40. package/dist/component/entities/indicatorForecasts.d.ts.map +1 -0
  41. package/dist/component/entities/indicatorForecasts.js +180 -0
  42. package/dist/component/entities/indicatorForecasts.js.map +1 -0
  43. package/dist/component/entities/indicatorValues.d.ts +77 -0
  44. package/dist/component/entities/indicatorValues.d.ts.map +1 -0
  45. package/dist/component/entities/indicatorValues.js +218 -0
  46. package/dist/component/entities/indicatorValues.js.map +1 -0
  47. package/dist/component/entities/indicators.d.ts +90 -0
  48. package/dist/component/entities/indicators.d.ts.map +1 -0
  49. package/dist/component/entities/indicators.js +239 -0
  50. package/dist/component/entities/indicators.js.map +1 -0
  51. package/dist/component/entities/initiatives.d.ts +103 -0
  52. package/dist/component/entities/initiatives.d.ts.map +1 -0
  53. package/dist/component/entities/initiatives.js +275 -0
  54. package/dist/component/entities/initiatives.js.map +1 -0
  55. package/dist/component/entities/keyResults.d.ts +111 -0
  56. package/dist/component/entities/keyResults.d.ts.map +1 -0
  57. package/dist/component/entities/keyResults.js +284 -0
  58. package/dist/component/entities/keyResults.js.map +1 -0
  59. package/dist/component/entities/milestones.d.ts +93 -0
  60. package/dist/component/entities/milestones.d.ts.map +1 -0
  61. package/dist/component/entities/milestones.js +249 -0
  62. package/dist/component/entities/milestones.js.map +1 -0
  63. package/dist/component/entities/objectives.d.ts +99 -0
  64. package/dist/component/entities/objectives.d.ts.map +1 -0
  65. package/dist/component/entities/objectives.js +261 -0
  66. package/dist/component/entities/objectives.js.map +1 -0
  67. package/dist/component/entities/risks.d.ts +126 -0
  68. package/dist/component/entities/risks.d.ts.map +1 -0
  69. package/dist/component/entities/risks.js +315 -0
  70. package/dist/component/entities/risks.js.map +1 -0
  71. package/dist/component/externalId.d.ts +79 -0
  72. package/dist/component/externalId.d.ts.map +1 -0
  73. package/dist/component/externalId.js +124 -0
  74. package/dist/component/externalId.js.map +1 -0
  75. package/dist/component/lib/hmac.d.ts +18 -0
  76. package/dist/component/lib/hmac.d.ts.map +1 -0
  77. package/dist/component/lib/hmac.js +35 -0
  78. package/dist/component/lib/hmac.js.map +1 -0
  79. package/dist/component/lib/index.d.ts +7 -0
  80. package/dist/component/lib/index.d.ts.map +1 -0
  81. package/dist/component/lib/index.js +6 -0
  82. package/dist/component/lib/index.js.map +1 -0
  83. package/dist/component/lib/types.d.ts +30 -0
  84. package/dist/component/lib/types.d.ts.map +1 -0
  85. package/dist/component/lib/types.js +7 -0
  86. package/dist/component/lib/types.js.map +1 -0
  87. package/dist/component/lib/validation.d.ts +15 -0
  88. package/dist/component/lib/validation.d.ts.map +1 -0
  89. package/dist/component/lib/validation.js +29 -0
  90. package/dist/component/lib/validation.js.map +1 -0
  91. package/dist/component/okrhub.d.ts +31 -0
  92. package/dist/component/okrhub.d.ts.map +1 -0
  93. package/dist/component/okrhub.js +45 -0
  94. package/dist/component/okrhub.js.map +1 -0
  95. package/dist/component/schema.d.ts +943 -0
  96. package/dist/component/schema.d.ts.map +1 -0
  97. package/dist/component/schema.js +437 -0
  98. package/dist/component/schema.js.map +1 -0
  99. package/dist/component/sync/http.d.ts +30 -0
  100. package/dist/component/sync/http.d.ts.map +1 -0
  101. package/dist/component/sync/http.js +114 -0
  102. package/dist/component/sync/http.js.map +1 -0
  103. package/dist/component/sync/index.d.ts +7 -0
  104. package/dist/component/sync/index.d.ts.map +1 -0
  105. package/dist/component/sync/index.js +7 -0
  106. package/dist/component/sync/index.js.map +1 -0
  107. package/dist/component/sync/processor.d.ts +20 -0
  108. package/dist/component/sync/processor.d.ts.map +1 -0
  109. package/dist/component/sync/processor.js +67 -0
  110. package/dist/component/sync/processor.js.map +1 -0
  111. package/dist/component/sync/queue.d.ts +40 -0
  112. package/dist/component/sync/queue.d.ts.map +1 -0
  113. package/dist/component/sync/queue.js +176 -0
  114. package/dist/component/sync/queue.js.map +1 -0
  115. package/dist/react/index.d.ts +2 -0
  116. package/dist/react/index.d.ts.map +1 -0
  117. package/dist/react/index.js +6 -0
  118. package/dist/react/index.js.map +1 -0
  119. package/package.json +117 -0
  120. package/src/client/_generated/_ignore.ts +1 -0
  121. package/src/client/index.ts +1004 -0
  122. package/src/component/_generated/api.ts +88 -0
  123. package/src/component/_generated/component.ts +2685 -0
  124. package/src/component/_generated/dataModel.ts +60 -0
  125. package/src/component/_generated/server.ts +156 -0
  126. package/src/component/convex.config.ts +3 -0
  127. package/src/component/entities/batch.ts +90 -0
  128. package/src/component/entities/index.ts +64 -0
  129. package/src/component/entities/indicatorForecasts.ts +205 -0
  130. package/src/component/entities/indicatorValues.ts +254 -0
  131. package/src/component/entities/indicators.ts +290 -0
  132. package/src/component/entities/initiatives.ts +342 -0
  133. package/src/component/entities/keyResults.ts +334 -0
  134. package/src/component/entities/milestones.ts +296 -0
  135. package/src/component/entities/objectives.ts +294 -0
  136. package/src/component/entities/risks.ts +383 -0
  137. package/src/component/externalId.ts +172 -0
  138. package/src/component/lib/hmac.ts +53 -0
  139. package/src/component/lib/index.ts +7 -0
  140. package/src/component/lib/types.ts +31 -0
  141. package/src/component/lib/validation.ts +41 -0
  142. package/src/component/okrhub.ts +110 -0
  143. package/src/component/schema.ts +574 -0
  144. package/src/component/sync/http.ts +138 -0
  145. package/src/component/sync/index.ts +11 -0
  146. package/src/component/sync/processor.ts +77 -0
  147. package/src/component/sync/queue.ts +201 -0
  148. package/src/react/index.ts +7 -0
@@ -0,0 +1,20 @@
1
+ /**
2
+ * Sync Processor for OKRHub Component
3
+ *
4
+ * Processes pending items from the sync queue.
5
+ */
6
+ /**
7
+ * Process pending items from the sync queue
8
+ * This should be called periodically (e.g., via cron job)
9
+ */
10
+ export declare const processSyncQueue: import("convex/server").RegisteredAction<"public", {
11
+ batchSize?: number | undefined;
12
+ apiKeyPrefix: string;
13
+ endpointUrl: string;
14
+ signingSecret: string;
15
+ }, Promise<{
16
+ processed: number;
17
+ succeeded: number;
18
+ failed: number;
19
+ }>>;
20
+ //# sourceMappingURL=processor.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"processor.d.ts","sourceRoot":"","sources":["../../../src/component/sync/processor.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAMH;;;GAGG;AACH,eAAO,MAAM,gBAAgB;;;;;;;;;GA8D3B,CAAC"}
@@ -0,0 +1,67 @@
1
+ /**
2
+ * Sync Processor for OKRHub Component
3
+ *
4
+ * Processes pending items from the sync queue.
5
+ */
6
+ import { v } from "convex/values";
7
+ import { action } from "../_generated/server.js";
8
+ import { api, internal } from "../_generated/api.js";
9
+ /**
10
+ * Process pending items from the sync queue
11
+ * This should be called periodically (e.g., via cron job)
12
+ */
13
+ export const processSyncQueue = action({
14
+ args: {
15
+ endpointUrl: v.string(),
16
+ apiKeyPrefix: v.string(),
17
+ signingSecret: v.string(),
18
+ batchSize: v.optional(v.number()),
19
+ },
20
+ returns: v.object({
21
+ processed: v.number(),
22
+ succeeded: v.number(),
23
+ failed: v.number(),
24
+ }),
25
+ handler: async (ctx, args) => {
26
+ const { endpointUrl, apiKeyPrefix, signingSecret, batchSize = 10 } = args;
27
+ // Get pending items
28
+ const pendingItems = await ctx.runQuery(api.sync.queue.getPendingSyncItems, { limit: batchSize });
29
+ let processed = 0;
30
+ let succeeded = 0;
31
+ let failed = 0;
32
+ for (const item of pendingItems) {
33
+ processed++;
34
+ // Mark as processing
35
+ await ctx.runMutation(internal.sync.queue.updateSyncQueueItem, {
36
+ id: item._id,
37
+ status: "processing",
38
+ });
39
+ // Send to LinkHub
40
+ const result = await ctx.runAction(api.sync.http.sendToLinkHub, {
41
+ endpointUrl,
42
+ apiKeyPrefix,
43
+ signingSecret,
44
+ entityType: item.entityType,
45
+ payload: item.payload,
46
+ });
47
+ if (result.success) {
48
+ succeeded++;
49
+ await ctx.runMutation(internal.sync.queue.updateSyncQueueItem, {
50
+ id: item._id,
51
+ status: "success",
52
+ linkHubId: "linkHubId" in result ? result.linkHubId : undefined,
53
+ });
54
+ }
55
+ else {
56
+ failed++;
57
+ await ctx.runMutation(internal.sync.queue.updateSyncQueueItem, {
58
+ id: item._id,
59
+ status: "failed",
60
+ errorMessage: result.error,
61
+ });
62
+ }
63
+ }
64
+ return { processed, succeeded, failed };
65
+ },
66
+ });
67
+ //# sourceMappingURL=processor.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"processor.js","sourceRoot":"","sources":["../../../src/component/sync/processor.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAEH,OAAO,EAAE,CAAC,EAAE,MAAM,eAAe,CAAC;AAClC,OAAO,EAAE,MAAM,EAAE,MAAM,yBAAyB,CAAC;AACjD,OAAO,EAAE,GAAG,EAAE,QAAQ,EAAE,MAAM,sBAAsB,CAAC;AAErD;;;GAGG;AACH,MAAM,CAAC,MAAM,gBAAgB,GAAG,MAAM,CAAC;IACrC,IAAI,EAAE;QACJ,WAAW,EAAE,CAAC,CAAC,MAAM,EAAE;QACvB,YAAY,EAAE,CAAC,CAAC,MAAM,EAAE;QACxB,aAAa,EAAE,CAAC,CAAC,MAAM,EAAE;QACzB,SAAS,EAAE,CAAC,CAAC,QAAQ,CAAC,CAAC,CAAC,MAAM,EAAE,CAAC;KAClC;IACD,OAAO,EAAE,CAAC,CAAC,MAAM,CAAC;QAChB,SAAS,EAAE,CAAC,CAAC,MAAM,EAAE;QACrB,SAAS,EAAE,CAAC,CAAC,MAAM,EAAE;QACrB,MAAM,EAAE,CAAC,CAAC,MAAM,EAAE;KACnB,CAAC;IACF,OAAO,EAAE,KAAK,EAAE,GAAG,EAAE,IAAI,EAAE,EAAE;QAC3B,MAAM,EAAE,WAAW,EAAE,YAAY,EAAE,aAAa,EAAE,SAAS,GAAG,EAAE,EAAE,GAAG,IAAI,CAAC;QAE1E,oBAAoB;QACpB,MAAM,YAAY,GAAG,MAAM,GAAG,CAAC,QAAQ,CACrC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,mBAAmB,EAClC,EAAE,KAAK,EAAE,SAAS,EAAE,CACrB,CAAC;QAEF,IAAI,SAAS,GAAG,CAAC,CAAC;QAClB,IAAI,SAAS,GAAG,CAAC,CAAC;QAClB,IAAI,MAAM,GAAG,CAAC,CAAC;QAEf,KAAK,MAAM,IAAI,IAAI,YAAY,EAAE,CAAC;YAChC,SAAS,EAAE,CAAC;YAEZ,qBAAqB;YACrB,MAAM,GAAG,CAAC,WAAW,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,mBAAmB,EAAE;gBAC7D,EAAE,EAAE,IAAI,CAAC,GAAG;gBACZ,MAAM,EAAE,YAAY;aACrB,CAAC,CAAC;YAEH,kBAAkB;YAClB,MAAM,MAAM,GAAG,MAAM,GAAG,CAAC,SAAS,CAAC,GAAG,CAAC,IAAI,CAAC,IAAI,CAAC,aAAa,EAAE;gBAC9D,WAAW;gBACX,YAAY;gBACZ,aAAa;gBACb,UAAU,EAAE,IAAI,CAAC,UAAU;gBAC3B,OAAO,EAAE,IAAI,CAAC,OAAO;aACtB,CAAC,CAAC;YAEH,IAAI,MAAM,CAAC,OAAO,EAAE,CAAC;gBACnB,SAAS,EAAE,CAAC;gBACZ,MAAM,GAAG,CAAC,WAAW,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,mBAAmB,EAAE;oBAC7D,EAAE,EAAE,IAAI,CAAC,GAAG;oBACZ,MAAM,EAAE,SAAS;oBACjB,SAAS,EAAE,WAAW,IAAI,MAAM,CAAC,CAAC,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,SAAS;iBAChE,CAAC,CAAC;YACL,CAAC;iBAAM,CAAC;gBACN,MAAM,EAAE,CAAC;gBACT,MAAM,GAAG,CAAC,WAAW,CAAC,QAAQ,CAAC,IAAI,CAAC,KAAK,CAAC,mBAAmB,EAAE;oBAC7D,EAAE,EAAE,IAAI,CAAC,GAAG;oBACZ,MAAM,EAAE,QAAQ;oBAChB,YAAY,EAAE,MAAM,CAAC,KAAK;iBAC3B,CAAC,CAAC;YACL,CAAC;QACH,CAAC;QAED,OAAO,EAAE,SAAS,EAAE,SAAS,EAAE,MAAM,EAAE,CAAC;IAC1C,CAAC;CACF,CAAC,CAAC"}
@@ -0,0 +1,40 @@
1
+ /**
2
+ * Sync Queue Management for OKRHub Component
3
+ *
4
+ * Handles the sync queue for async processing of entities to LinkHub.
5
+ */
6
+ /**
7
+ * Adds an item to the sync queue for async processing
8
+ */
9
+ export declare const addToSyncQueue: import("convex/server").RegisteredMutation<"internal", {
10
+ externalId: string;
11
+ entityType: string;
12
+ payload: string;
13
+ }, Promise<import("convex/values").GenericId<"syncQueue">>>;
14
+ /**
15
+ * Updates sync queue item status and the local entity syncStatus
16
+ */
17
+ export declare const updateSyncQueueItem: import("convex/server").RegisteredMutation<"internal", {
18
+ errorMessage?: string | undefined;
19
+ linkHubId?: string | undefined;
20
+ id: import("convex/values").GenericId<"syncQueue">;
21
+ status: "pending" | "failed" | "processing" | "success";
22
+ }, Promise<void>>;
23
+ /**
24
+ * Gets pending items from the sync queue
25
+ */
26
+ export declare const getPendingSyncItems: import("convex/server").RegisteredQuery<"public", {
27
+ limit?: number | undefined;
28
+ }, Promise<{
29
+ _id: import("convex/values").GenericId<"syncQueue">;
30
+ _creationTime: number;
31
+ lastAttemptAt?: number | undefined;
32
+ errorMessage?: string | undefined;
33
+ externalId: string;
34
+ createdAt: number;
35
+ status: "pending" | "failed" | "processing" | "success";
36
+ entityType: string;
37
+ payload: string;
38
+ attempts: number;
39
+ }[]>>;
40
+ //# sourceMappingURL=queue.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"queue.d.ts","sourceRoot":"","sources":["../../../src/component/sync/queue.ts"],"names":[],"mappings":"AAAA;;;;GAIG;AAKH;;GAEG;AACH,eAAO,MAAM,cAAc;;;;2DAgBzB,CAAC;AAEH;;GAEG;AACH,eAAO,MAAM,mBAAmB;;;;;iBA0I9B,CAAC;AAEH;;GAEG;AACH,eAAO,MAAM,mBAAmB;;;;;;;;;;;;;KAwB9B,CAAC"}
@@ -0,0 +1,176 @@
1
+ /**
2
+ * Sync Queue Management for OKRHub Component
3
+ *
4
+ * Handles the sync queue for async processing of entities to LinkHub.
5
+ */
6
+ import { v } from "convex/values";
7
+ import { internalMutation, query } from "../_generated/server.js";
8
+ /**
9
+ * Adds an item to the sync queue for async processing
10
+ */
11
+ export const addToSyncQueue = internalMutation({
12
+ args: {
13
+ entityType: v.string(),
14
+ externalId: v.string(),
15
+ payload: v.string(),
16
+ },
17
+ handler: async (ctx, args) => {
18
+ return await ctx.db.insert("syncQueue", {
19
+ entityType: args.entityType,
20
+ externalId: args.externalId,
21
+ payload: args.payload,
22
+ status: "pending",
23
+ attempts: 0,
24
+ createdAt: Date.now(),
25
+ });
26
+ },
27
+ });
28
+ /**
29
+ * Updates sync queue item status and the local entity syncStatus
30
+ */
31
+ export const updateSyncQueueItem = internalMutation({
32
+ args: {
33
+ id: v.id("syncQueue"),
34
+ status: v.union(v.literal("pending"), v.literal("processing"), v.literal("success"), v.literal("failed")),
35
+ errorMessage: v.optional(v.string()),
36
+ linkHubId: v.optional(v.string()),
37
+ },
38
+ handler: async (ctx, args) => {
39
+ const updates = {
40
+ status: args.status,
41
+ lastAttemptAt: Date.now(),
42
+ };
43
+ if (args.errorMessage) {
44
+ updates.errorMessage = args.errorMessage;
45
+ }
46
+ const item = await ctx.db.get(args.id);
47
+ if (item) {
48
+ updates.attempts = item.attempts + 1;
49
+ }
50
+ await ctx.db.patch(args.id, updates);
51
+ // If successful, update the local entity syncStatus and log the sync
52
+ if (args.status === "success" && item) {
53
+ // Update local entity syncStatus based on entityType
54
+ const newSyncStatus = "synced";
55
+ if (item.entityType === "objective") {
56
+ const entity = await ctx.db
57
+ .query("objectives")
58
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
59
+ .first();
60
+ if (entity) {
61
+ await ctx.db.patch(entity._id, {
62
+ syncStatus: newSyncStatus,
63
+ updatedAt: Date.now(),
64
+ });
65
+ }
66
+ }
67
+ else if (item.entityType === "keyResult") {
68
+ const entity = await ctx.db
69
+ .query("keyResults")
70
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
71
+ .first();
72
+ if (entity) {
73
+ await ctx.db.patch(entity._id, {
74
+ syncStatus: newSyncStatus,
75
+ updatedAt: Date.now(),
76
+ });
77
+ }
78
+ }
79
+ else if (item.entityType === "risk") {
80
+ const entity = await ctx.db
81
+ .query("risks")
82
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
83
+ .first();
84
+ if (entity) {
85
+ await ctx.db.patch(entity._id, { syncStatus: newSyncStatus });
86
+ }
87
+ }
88
+ else if (item.entityType === "initiative") {
89
+ const entity = await ctx.db
90
+ .query("initiatives")
91
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
92
+ .first();
93
+ if (entity) {
94
+ await ctx.db.patch(entity._id, {
95
+ syncStatus: newSyncStatus,
96
+ updatedAt: Date.now(),
97
+ });
98
+ }
99
+ }
100
+ else if (item.entityType === "indicator") {
101
+ const entity = await ctx.db
102
+ .query("indicators")
103
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
104
+ .first();
105
+ if (entity) {
106
+ await ctx.db.patch(entity._id, { syncStatus: newSyncStatus });
107
+ }
108
+ }
109
+ else if (item.entityType === "indicatorValue") {
110
+ const entity = await ctx.db
111
+ .query("indicatorValues")
112
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
113
+ .first();
114
+ if (entity) {
115
+ await ctx.db.patch(entity._id, { syncStatus: newSyncStatus });
116
+ }
117
+ }
118
+ else if (item.entityType === "indicatorForecast") {
119
+ const entity = await ctx.db
120
+ .query("indicatorForecasts")
121
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
122
+ .first();
123
+ if (entity) {
124
+ await ctx.db.patch(entity._id, { syncStatus: newSyncStatus });
125
+ }
126
+ }
127
+ else if (item.entityType === "milestone") {
128
+ const entity = await ctx.db
129
+ .query("milestones")
130
+ .withIndex("by_external_id", (q) => q.eq("externalId", item.externalId))
131
+ .first();
132
+ if (entity) {
133
+ await ctx.db.patch(entity._id, {
134
+ syncStatus: newSyncStatus,
135
+ updatedAt: Date.now(),
136
+ });
137
+ }
138
+ }
139
+ // Log the sync
140
+ await ctx.db.insert("syncLog", {
141
+ entityType: item.entityType,
142
+ externalId: item.externalId,
143
+ linkHubId: args.linkHubId,
144
+ syncedAt: Date.now(),
145
+ action: "create", // TODO: Determine if create or update
146
+ });
147
+ }
148
+ },
149
+ });
150
+ /**
151
+ * Gets pending items from the sync queue
152
+ */
153
+ export const getPendingSyncItems = query({
154
+ args: {
155
+ limit: v.optional(v.number()),
156
+ },
157
+ returns: v.array(v.object({
158
+ _id: v.id("syncQueue"),
159
+ _creationTime: v.number(),
160
+ entityType: v.string(),
161
+ externalId: v.string(),
162
+ payload: v.string(),
163
+ status: v.string(),
164
+ attempts: v.number(),
165
+ lastAttemptAt: v.optional(v.number()),
166
+ errorMessage: v.optional(v.string()),
167
+ createdAt: v.number(),
168
+ })),
169
+ handler: async (ctx, args) => {
170
+ return await ctx.db
171
+ .query("syncQueue")
172
+ .withIndex("by_status", (q) => q.eq("status", "pending"))
173
+ .take(args.limit ?? 50);
174
+ },
175
+ });
176
+ //# sourceMappingURL=queue.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"queue.js","sourceRoot":"","sources":["../../../src/component/sync/queue.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,2 @@
1
+ export declare const useMyComponent: () => {};
2
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../../src/react/index.ts"],"names":[],"mappings":"AAIA,eAAO,MAAM,cAAc,UAE1B,CAAC"}
@@ -0,0 +1,6 @@
1
+ "use client";
2
+ // This is where React components / hooks go.
3
+ export const useMyComponent = () => {
4
+ return {};
5
+ };
6
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../../src/react/index.ts"],"names":[],"mappings":"AAAA,YAAY,CAAC;AAEb,6CAA6C;AAE7C,MAAM,CAAC,MAAM,cAAc,GAAG,GAAG,EAAE;IACjC,OAAO,EAAE,CAAC;AACZ,CAAC,CAAC"}
package/package.json ADDED
@@ -0,0 +1,117 @@
1
+ {
2
+ "name": "@okrlinkhub/okrhub",
3
+ "description": "Convex component for syncing OKR data (Objectives, Key Results, Risks, Initiatives) to LinkHub via secure HMAC-authenticated API.",
4
+ "repository": "github:okrlinkhub/okrhub-convex",
5
+ "homepage": "https://github.com/okrlinkhub/okrhub-convex#readme",
6
+ "bugs": {
7
+ "url": "https://github.com/okrlinkhub/okrhub-convex/issues"
8
+ },
9
+ "version": "0.1.0",
10
+ "license": "Apache-2.0",
11
+ "keywords": [
12
+ "convex",
13
+ "component",
14
+ "okr",
15
+ "objectives",
16
+ "key-results",
17
+ "linkhub",
18
+ "kpi",
19
+ "risks",
20
+ "initiatives"
21
+ ],
22
+ "type": "module",
23
+ "scripts": {
24
+ "dev": "run-p -r 'dev:*'",
25
+ "dev:backend": "convex dev --typecheck-components",
26
+ "dev:frontend": "cd example && vite --clearScreen false",
27
+ "dev:build": "chokidar 'tsconfig*.json' 'src/**/*.ts' -i '**/*.test.ts' -c 'npm run build:codegen' --initial",
28
+ "predev": "path-exists .env.local dist || (npm run build && convex dev --once)",
29
+ "build": "tsc --project ./tsconfig.build.json",
30
+ "build:codegen": "npx convex codegen --component-dir ./src/component && npm run build",
31
+ "build:clean": "rm -rf dist *.tsbuildinfo && npm run build:codegen",
32
+ "typecheck": "tsc --noEmit && tsc -p example && tsc -p example/convex",
33
+ "lint": "eslint .",
34
+ "all": "run-p -r 'dev:*' 'test:watch'",
35
+ "test": "vitest run --typecheck",
36
+ "test:watch": "vitest --typecheck --clearScreen false",
37
+ "test:debug": "vitest --inspect-brk --no-file-parallelism",
38
+ "test:coverage": "vitest run --coverage --coverage.reporter=text",
39
+ "preversion": "npm ci && npm run build:clean && run-p test lint typecheck",
40
+ "prepublishOnly": "npm whoami || npm login",
41
+ "alpha": "npm version prerelease --preid alpha && npm publish --tag alpha && git push --follow-tags",
42
+ "release": "npm version patch && npm publish && git push --follow-tags",
43
+ "version": "vim -c 'normal o' -c 'normal o## '$npm_package_version CHANGELOG.md && prettier -w CHANGELOG.md && git add CHANGELOG.md"
44
+ },
45
+ "files": [
46
+ "dist",
47
+ "src"
48
+ ],
49
+ "exports": {
50
+ "./package.json": "./package.json",
51
+ ".": {
52
+ "types": "./dist/client/index.d.ts",
53
+ "default": "./dist/client/index.js"
54
+ },
55
+ "./schema": {
56
+ "types": "./dist/component/schema.d.ts",
57
+ "default": "./dist/component/schema.js"
58
+ },
59
+ "./externalId": {
60
+ "types": "./dist/component/externalId.d.ts",
61
+ "default": "./dist/component/externalId.js"
62
+ },
63
+ "./react": {
64
+ "types": "./dist/react/index.d.ts",
65
+ "default": "./dist/react/index.js"
66
+ },
67
+ "./_generated/component.js": {
68
+ "types": "./dist/component/_generated/component.d.ts"
69
+ },
70
+ "./_generated/component": {
71
+ "types": "./dist/component/_generated/component.d.ts"
72
+ },
73
+ "./convex.config.js": {
74
+ "types": "./dist/component/convex.config.d.ts",
75
+ "default": "./dist/component/convex.config.js"
76
+ },
77
+ "./convex.config": {
78
+ "types": "./dist/component/convex.config.d.ts",
79
+ "default": "./dist/component/convex.config.js"
80
+ }
81
+ },
82
+ "peerDependencies": {
83
+ "convex": "^1.31.6",
84
+ "react": "^18.3.1 || ^19.0.0"
85
+ },
86
+ "devDependencies": {
87
+ "@convex-dev/eslint-plugin": "^1.1.1",
88
+ "@edge-runtime/vm": "^5.0.0",
89
+ "@eslint/eslintrc": "^3.3.3",
90
+ "@eslint/js": "9.39.2",
91
+ "@types/node": "^24.10.9",
92
+ "@types/react": "^19.2.9",
93
+ "@types/react-dom": "^19.2.3",
94
+ "@vitejs/plugin-react": "^5.1.2",
95
+ "chokidar-cli": "3.0.0",
96
+ "convex": "1.31.6",
97
+ "convex-test": "0.0.41",
98
+ "cpy-cli": "^6.0.0",
99
+ "eslint": "9.39.2",
100
+ "eslint-plugin-react": "^7.37.5",
101
+ "eslint-plugin-react-hooks": "^7.0.1",
102
+ "eslint-plugin-react-refresh": "^0.4.26",
103
+ "globals": "^17.1.0",
104
+ "npm-run-all2": "8.0.4",
105
+ "path-exists-cli": "2.0.0",
106
+ "pkg-pr-new": "^0.0.62",
107
+ "prettier": "3.8.1",
108
+ "react": "^19.2.3",
109
+ "react-dom": "^19.2.3",
110
+ "typescript": "5.9.3",
111
+ "typescript-eslint": "8.53.1",
112
+ "vite": "7.3.1",
113
+ "vitest": "4.0.18"
114
+ },
115
+ "types": "./dist/client/index.d.ts",
116
+ "module": "./dist/client/index.js"
117
+ }
@@ -0,0 +1 @@
1
+ // This is only here so convex-test can detect a _generated folder