-
-
Notifications
You must be signed in to change notification settings - Fork 45
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Schema 8 #228
Draft
jthrilly
wants to merge
19
commits into
next
Choose a base branch
from
schema-8
base: next
Could not load branches
Branch not found: {{ refName }}
Loading
Could not load tags
Nothing to show
Loading
Are you sure you want to change the base?
Some commits from the old base branch may be removed from the timeline,
and old review comments may become outdated.
Draft
Schema 8 #228
Changes from 9 commits
Commits
Show all changes
19 commits
Select commit
Hold shift + click to select a range
401d3c9
add protocol validation lib
jthrilly 7d273b7
inline protocol-validation lib
jthrilly 3fc3ab0
protocol-validation tests
jthrilly 014a9eb
update snapshots
jthrilly a9f5434
add todo for missing migration tests
jthrilly d799027
reorganize schemas and add scripts to package.json
jthrilly 5ffbde1
add test protocol
jthrilly 29bf413
ignore protocol-validation ts errors for now
jthrilly ae6953b
fix outstanding errors relating to protocol validation lib
jthrilly 5a5dcb9
Merge branch 'next' into schema-8
jthrilly a12afae
Merge branch 'main' into schema-8
jthrilly 2ff4c0e
update pnpm lock
jthrilly 5cebd70
sync with next
jthrilly f6be250
change the way reset is called to bypass TS error
jthrilly 87b983c
update redux, redux toolkit, and typescript errors related to react a…
jthrilly caa6b41
remove deviceSettings entirely; switch build action to run on node 22
jthrilly a56bb37
fix errors related to redux upgrade
jthrilly cd154dd
remove unused utility
jthrilly b0f5773
re add thunk middleware to drag and drop store
jthrilly File filter
Filter by extension
Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
128 changes: 128 additions & 0 deletions
128
lib/protocol-validation/__tests__/test-protocols.test.ts
There was a problem hiding this comment. Choose a reason for hiding this commentThe reason will be displayed to describe this comment to others. Learn more. This needs to be implemented or removed before merging |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,128 @@ | ||
import { execSync } from 'child_process'; | ||
import { createDecipheriv } from 'crypto'; | ||
import { readFile, writeFile } from 'fs/promises'; | ||
import type Zip from 'jszip'; | ||
import JSZip from 'jszip'; | ||
import { join } from 'path'; | ||
import { describe, it } from 'vitest'; | ||
import { validateProtocol } from '../index'; | ||
|
||
// Utility functions for encryption handling | ||
const decryptFile = async ( | ||
encryptedBuffer: Buffer, | ||
key: string, | ||
iv: string, | ||
): Promise<Buffer> => { | ||
const decipher = createDecipheriv( | ||
'aes-256-cbc', | ||
Buffer.from(key, 'hex'), | ||
Buffer.from(iv, 'hex'), | ||
); | ||
const decrypted = Buffer.concat([ | ||
decipher.update(encryptedBuffer), | ||
decipher.final(), | ||
]); | ||
return decrypted; | ||
}; | ||
|
||
const downloadAndDecryptProtocols = async (tempDir: string): Promise<void> => { | ||
const encryptionKey = process.env.PROTOCOL_ENCRYPTION_KEY; | ||
const encryptionIv = process.env.PROTOCOL_ENCRYPTION_IV; | ||
|
||
if (!encryptionKey || !encryptionIv) { | ||
throw new Error( | ||
'Encryption key and IV must be set in environment variables', | ||
); | ||
} | ||
|
||
// Download encrypted protocols from GitHub LFS | ||
// Replace with your actual GitHub repository URL | ||
const githubUrl = | ||
'https://github.com/YOUR_ORG/YOUR_REPO/raw/main/test-protocols.tar.gz.enc'; | ||
|
||
try { | ||
console.log('Downloading encrypted protocols...'); | ||
execSync( | ||
`curl -L -o ${join(tempDir, 'protocols.tar.gz.enc')} ${githubUrl}`, | ||
); | ||
|
||
// Decrypt the file | ||
console.log('Decrypting protocols...'); | ||
const encryptedData = await readFile(join(tempDir, 'protocols.tar.gz.enc')); | ||
const decryptedData = await decryptFile( | ||
encryptedData, | ||
encryptionKey, | ||
encryptionIv, | ||
); | ||
await writeFile(join(tempDir, 'protocols.tar.gz'), decryptedData); | ||
|
||
// Extract the tar.gz file | ||
console.log('Extracting protocols...'); | ||
execSync(`tar -xzf ${join(tempDir, 'protocols.tar.gz')} -C ${tempDir}`); | ||
} catch (error) { | ||
console.error('Error preparing protocols:', error); | ||
throw error; | ||
} | ||
}; | ||
|
||
export const getProtocolJsonAsObject = async (zip: Zip) => { | ||
const protocolString = await zip.file('protocol.json')?.async('string'); | ||
|
||
if (!protocolString) { | ||
throw new Error('protocol.json not found in zip'); | ||
} | ||
|
||
const protocol = await JSON.parse(protocolString); | ||
return protocol; | ||
}; | ||
|
||
const extractAndValidate = async (protocolPath: string) => { | ||
const buffer = await readFile(protocolPath); | ||
const zip = await JSZip.loadAsync(buffer); | ||
const protocol = await getProtocolJsonAsObject(zip); | ||
|
||
let schemaVersion = undefined; | ||
if (!protocol.schemaVersion || protocol.schemaVersion === '1.0.0') { | ||
console.log('schemaVersion is missing or "1.0.0" for', protocolPath); | ||
schemaVersion = 1; | ||
} | ||
|
||
return await validateProtocol(protocol, schemaVersion); | ||
}; | ||
|
||
// Create temporary directory for test protocols | ||
let tempDir: string; | ||
|
||
describe('Test protocols', () => { | ||
it.todo('should validate all test protocols'); | ||
|
||
// beforeAll(async () => { | ||
// // Create temporary directory | ||
// tempDir = mkdtempSync(join(tmpdir(), 'test-protocols-')); | ||
|
||
// // Skip download in CI if protocols are already present | ||
// if (process.env.CI && process.env.SKIP_PROTOCOL_DOWNLOAD) { | ||
// console.log('Skipping protocol download in CI'); | ||
// return; | ||
// } | ||
|
||
// await downloadAndDecryptProtocols(tempDir); | ||
// }); | ||
|
||
// afterAll(() => { | ||
// // Clean up temporary directory | ||
// rmSync(tempDir, { recursive: true, force: true }); | ||
// }); | ||
|
||
// it.each(readdirSync(tempDir).filter((file) => file.endsWith('.netcanvas')))( | ||
// '%s', | ||
// async (protocol) => { | ||
// const protocolPath = join(tempDir, protocol); | ||
// const result = await extractAndValidate(protocolPath); | ||
|
||
// expect(result.isValid).toBe(true); | ||
// expect(result.schemaErrors).toEqual([]); | ||
// expect(result.logicErrors).toEqual([]); | ||
// }, | ||
// ); | ||
}); |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,49 @@ | ||
import { type Protocol } from '@codaco/shared-consts'; | ||
import { ensureError } from '~/utils/ensureError'; | ||
import { validateLogic } from './validation/validateLogic'; | ||
import { validateSchema } from './validation/validateSchema'; | ||
|
||
export type ValidationError = { | ||
path: string; | ||
message: string; | ||
}; | ||
|
||
type ValidationResult = { | ||
isValid: boolean; | ||
schemaErrors: ValidationError[]; | ||
logicErrors: ValidationError[]; | ||
schemaVersion: number; | ||
schemaForced: boolean; | ||
}; | ||
|
||
const validateProtocol = async ( | ||
protocol: Protocol, | ||
forceSchemaVersion?: number, | ||
) => { | ||
if (protocol === undefined) { | ||
throw new Error('Protocol is undefined'); | ||
} | ||
|
||
try { | ||
const { hasErrors: hasSchemaErrors, errors: schemaErrors } = | ||
await validateSchema(protocol, forceSchemaVersion); | ||
const { hasErrors: hasLogicErrors, errors: logicErrors } = | ||
validateLogic(protocol); | ||
|
||
return { | ||
isValid: !hasSchemaErrors && !hasLogicErrors, | ||
schemaErrors, | ||
logicErrors, | ||
schemaVersion: protocol.schemaVersion, | ||
schemaForced: forceSchemaVersion !== undefined, | ||
} as ValidationResult; | ||
} catch (e) { | ||
const error = ensureError(e); | ||
|
||
throw new Error( | ||
`Protocol validation failed due to an internal error: ${error.message}`, | ||
); | ||
} | ||
}; | ||
|
||
export { validateProtocol, }; |
23 changes: 23 additions & 0 deletions
23
lib/protocol-validation/migrations/__tests__/getMigrationPath.test.js
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,23 @@ | ||
import { describe, expect, it } from 'vitest'; | ||
import getMigrationPath from '../getMigrationPath'; | ||
|
||
/** | ||
* Migrations are run in the order that they are defined relative to one another | ||
* e.g. 1 -> 3, will run 1 -> 2 -> 3 | ||
*/ | ||
|
||
describe('getMigrationPath', () => { | ||
it('gets the correct migration path for a protocol', () => { | ||
const migrationPath = getMigrationPath(1, 4); | ||
|
||
expect(migrationPath.length).toBe(3); | ||
|
||
expect(migrationPath).toEqual( | ||
expect.arrayContaining([ | ||
expect.objectContaining({ version: 2 }), | ||
expect.objectContaining({ version: 3 }), | ||
expect.objectContaining({ version: 4 }), | ||
]), | ||
); | ||
}); | ||
}); |
Oops, something went wrong.
Add this suggestion to a batch that can be applied as a single commit.
This suggestion is invalid because no changes were made to the code.
Suggestions cannot be applied while the pull request is closed.
Suggestions cannot be applied while viewing a subset of changes.
Only one suggestion per line can be applied in a batch.
Add this suggestion to a batch that can be applied as a single commit.
Applying suggestions on deleted lines is not supported.
You must change the existing code in this line in order to create a valid suggestion.
Outdated suggestions cannot be applied.
This suggestion has been applied or marked resolved.
Suggestions cannot be applied from pending reviews.
Suggestions cannot be applied on multi-line comments.
Suggestions cannot be applied while the pull request is queued to merge.
Suggestion cannot be applied right now. Please check back later.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Do not merge without removing this