-
-
Notifications
You must be signed in to change notification settings - Fork 14
Examples
Pantelis Georgiadis edited this page Oct 25, 2024
·
8 revisions
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CEchoRequest } = dcmjsDimse.requests;
const { Status } = dcmjsDimse.constants;
const client = new Client();
const request = new CEchoRequest();
request.on('response', (response) => {
if (response.getStatus() === Status.Success) {
console.log('Happy!');
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client, Implementation } = dcmjsDimse;
const { CEchoRequest } = dcmjsDimse.requests;
const { Status, UserIdentityType } = dcmjsDimse.constants;
Implementation.setImplementationClassUid('1.2.826.0.1.3680043.10.854');
Implementation.setImplementationVersion('DCMJS-DIMSE-V0.1');
const client = new Client();
const request = new CEchoRequest();
request.on('response', (response) => {
if (response.getStatus() === Status.Success) {
console.log('Happy!');
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP', {
securityOptions: {
key: Buffer.from(keyBuffer),
cert: Buffer.from(certBuffer),
ca: Buffer.from(caBuffer),
rejectUnauthorized: false,
requestCert: false,
},
userIdentity: {
type: UserIdentityType.UsernameAndPasscode,
positiveResponseRequested: true,
primaryField: username,
secondaryField: password,
},
});
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CFindRequest } = dcmjsDimse.requests;
const { Status } = dcmjsDimse.constants;
const client = new Client();
const request = CFindRequest.createStudyFindRequest({ PatientID: '12345', PatientName: '*' });
request.on('response', (response) => {
if (response.getStatus() === Status.Pending && response.hasDataset()) {
console.log(response.getDataset());
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CFindRequest } = dcmjsDimse.requests;
const { Status } = dcmjsDimse.constants;
const client = new Client();
const request = CFindRequest.createWorklistFindRequest({ PatientName: '*' });
request.on('response', (response) => {
if (response.getStatus() === Status.Pending && response.hasDataset()) {
console.log(response.getDataset());
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CStoreRequest } = dcmjsDimse.requests;
const client = new Client();
const request = new CStoreRequest('test.dcm');
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CMoveRequest } = dcmjsDimse.requests;
const { Status } = dcmjsDimse.constants;
const client = new Client();
const request = CMoveRequest.createStudyMoveRequest('DEST-AE', studyInstanceUid);
request.on('response', (response) => {
if (response.getStatus() === Status.Pending) {
console.log('Remaining: ' + response.getRemaining());
console.log('Completed: ' + response.getCompleted());
console.log('Warning: ' + response.getWarnings());
console.log('Failed: ' + response.getFailures());
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { CGetRequest } = dcmjsDimse.requests;
const { CStoreResponse } = dcmjsDimse.responses;
const { Status } = dcmjsDimse.constants;
const client = new Client();
const request = CGetRequest.createStudyGetRequest(studyInstanceUid);
request.on('response', (response) => {
if (response.getStatus() === Status.Pending) {
console.log('Remaining: ' + response.getRemaining());
console.log('Completed: ' + response.getCompleted());
console.log('Warning: ' + response.getWarnings());
console.log('Failed: ' + response.getFailures());
}
});
client.on('cStoreRequest', (request, callback) => {
console.log(request.getDataset());
const response = CStoreResponse.fromRequest(request);
response.setStatus(Status.Success);
callback(response);
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client, Dataset } = dcmjsDimse;
const { NActionRequest } = dcmjsDimse.requests;
const { NEventReportResponse } = dcmjsDimse.responses;
const { SopClass, Status, StorageClass } = dcmjsDimse.constants;
const client = new Client();
const request = new NActionRequest(
SopClass.StorageCommitmentPushModel,
Dataset.generateDerivedUid(),
0x0001
);
request.setDataset(
new Dataset({
TransactionUID: Dataset.generateDerivedUid(),
ReferencedSOPSequence: [
{
ReferencedSOPClassUID: StorageClass.MrImageStorage,
ReferencedSOPInstanceUID: Dataset.generateDerivedUid(),
},
],
})
);
client.addRequest(request);
client.on('nEventReportRequest', (request, callback) => {
console.log(request.getDataset());
const response = NEventReportResponse.fromRequest(request);
response.setStatus(Status.Success);
callback(response);
});
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
// Linger the association to get a synchronous
// storage commitment response
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP', {
associationLingerTimeout: 5000,
});
const dcmjsDimse = require('dcmjs-dimse');
const { Client, Dataset } = dcmjsDimse;
const { NCreateRequest } = dcmjsDimse.requests;
const { SopClass, Status, StorageClass } = dcmjsDimse.constants;
const client = new Client();
const request = new NCreateRequest(SopClass.InstanceAvailabilityNotification, '');
request.setDataset(
new Dataset({
StudyInstanceUID: Dataset.generateDerivedUid(),
ReferencedPerformedProcedureStepSequence: [],
ReferencedSeriesSequence: [
{
SeriesInstanceUID: Dataset.generateDerivedUid(),
ReferencedSOPSequence: [
{
ReferencedSOPClassUID: StorageClass.MrImageStorage,
ReferencedSOPInstanceUID: Dataset.generateDerivedUid(),
RetrieveAETitle: 'ANY-SCP',
InstanceAvailability: 'ONLINE',
},
],
},
],
})
);
request.on('response', (response) => {
if (response.getStatus() === Status.Success) {
console.log('Notified!');
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client } = dcmjsDimse;
const { NGetRequest } = dcmjsDimse.requests;
const { SopClass, Status } = dcmjsDimse.constants;
const client = new Client();
const request = new NGetRequest(SopClass.Printer, '1.2.840.10008.5.1.1.17', [
'PrinterStatus',
'PrinterStatusInfo',
'PrinterName',
'Manufacturer',
'ManufacturersModelName',
'DeviceSerialNumber',
'SoftwareVersions',
'DeviceSerialNumber',
'DateOfLastCalibration',
'TimeOfLastCalibration',
]);
request.on('response', (response) => {
if (response.getStatus() === Status.Success) {
console.log(response.getDataset());
}
});
client.addRequest(request);
client.on('networkError', (e) => {
console.log('Network error: ', e);
});
client.send('127.0.0.1', 12345, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Client, Dataset } = dcmjsDimse;
const { PresentationContext } = dcmjsDimse.association;
const { NActionRequest, NCreateRequest, NDeleteRequest, NSetRequest } = dcmjsDimse.requests;
const { SopClass, Status, TransferSyntax } = dcmjsDimse.constants;
const client = new Client();
const pc = new PresentationContext(
0,
SopClass.BasicGrayscalePrintManagementMeta,
TransferSyntax.ImplicitVRLittleEndian
);
client.addAdditionalPresentationContext(pc);
let filmSessionCreateRequest;
let filmBoxCreateRequest;
let imageBoxSetRequest;
let filmBoxPrintRequest;
let filmBoxDeleteRequest;
let filmSessionDeleteRequest;
// Create film session
filmSessionCreateRequest = new NCreateRequest(
SopClass.BasicFilmSession,
'', // No need to provide a UID
SopClass.BasicGrayscalePrintManagementMeta
);
filmSessionCreateRequest.setDataset(
new Dataset({
FilmDestination: 'MAGAZINE',
FilmSessionLabel: '',
MediumType: '',
NumberOfCopies: 1,
PrintPriority: 'MED',
})
);
filmSessionCreateRequest.on('response', (response) => {
if (response.getStatus() === Status.Success) {
// Set the referenced film session sequence of the film box creation request
// that is returned in the response of the film session creation request
const filmBoxDataset = filmBoxCreateRequest.getDataset();
filmBoxDataset.setElement('ReferencedFilmSessionSequence', [
{
ReferencedSOPClassUID: SopClass.BasicFilmSession,
ReferencedSOPInstanceUID: response.getAffectedSopInstanceUid(),
},
]);
// Set the requested SOP instance UID of the film session delete request
// that is returned in the response of the film session creation request
filmSessionDeleteRequest.setRequestedSopInstanceUid(response.getAffectedSopInstanceUid());
}
});
client.addRequest(filmSessionCreateRequest);
// Create film box
filmBoxCreateRequest = new NCreateRequest(
SopClass.BasicFilmBox,
'', // No need to provide a UID
SopClass.BasicGrayscalePrintManagementMeta
);
filmBoxCreateRequest.setDataset(
new Dataset({
ConfigurationInformation: '',
FilmOrientation: 'PORTRAIT',
FilmSizeID: '14INX14IN',
ImageDisplayFormat: 'STANDARD\\1,1',
MagnificationType: 'CUBIC',
})
);
filmBoxCreateRequest.on('response', (response) => {
if (response.getStatus() === Status.Success) {
// Set the requested SOP instance UID of the film box print request
// that is returned in the response of the film box creation request
filmBoxPrintRequest.setRequestedSopInstanceUid(response.getAffectedSopInstanceUid());
// Set the requested SOP instance UID of the film box delete request
// that is returned in the response of the film box creation request
filmBoxDeleteRequest.setRequestedSopInstanceUid(response.getAffectedSopInstanceUid());
// Set the requested SOP instance UID of the image box set creation request
// that is returned in the response of the film box creation request
const dataset = response.getDataset();
const referencedImageBoxSequenceItem = dataset.getElement('ReferencedImageBoxSequence');
imageBoxSetRequest.setRequestedSopInstanceUid(
referencedImageBoxSequenceItem.ReferencedSOPInstanceUID
);
}
});
client.addRequest(filmBoxCreateRequest);
// Set image box
imageBoxSetRequest = new NSetRequest(
SopClass.BasicGrayscaleImageBox,
'', // UID will be set once received
SopClass.BasicGrayscalePrintManagementMeta
);
// Create a random image
const width = 256;
const height = 256;
const pixels = new Uint8Array(width * height);
for (let i = 0; i < height; i++) {
for (let j = 0; j < width; j++) {
pixels[j * width + i] = Math.floor(Math.random() * Math.pow(2, 8) - 1);
}
}
imageBoxSetRequest.setDataset(
new Dataset({
ImageBoxPosition: 1,
Polarity: 'NORMAL',
RequestedDecimateCropBehavior: 'CROP',
BasicGrayscaleImageSequence: [
{
_vrMap: {
PixelData: 'OB',
},
Columns: width,
Rows: height,
BitsAllocated: 8,
BitsStored: 8,
HighBit: 7,
PixelRepresentation: 0,
SamplesPerPixel: 1,
PhotometricInterpretation: 'MONOCHROME2',
PixelData: [pixels.buffer],
},
],
})
);
client.addRequest(imageBoxSetRequest);
// Print film box!
filmBoxPrintRequest = new NActionRequest(
SopClass.BasicFilmBox,
'', // UID will be set once received
0x001,
SopClass.BasicGrayscalePrintManagementMeta
);
client.addRequest(filmBoxPrintRequest);
// Delete film box
filmBoxDeleteRequest = new NDeleteRequest(
SopClass.BasicFilmBox,
'', // UID will be set once received
SopClass.BasicGrayscalePrintManagementMeta
);
client.addRequest(filmBoxDeleteRequest);
// Delete film session
filmSessionDeleteRequest = new NDeleteRequest(
SopClass.BasicFilmSession,
'', // UID will be set once received
SopClass.BasicGrayscalePrintManagementMeta
);
client.addRequest(filmSessionDeleteRequest);
// Send requests
client.send('127.0.0.1', 104, 'SCU', 'ANY-SCP');
const dcmjsDimse = require('dcmjs-dimse');
const { Dataset, Server, Scp } = dcmjsDimse;
const { CEchoResponse, CFindResponse, CStoreResponse } = dcmjsDimse.responses;
const {
Status,
PresentationContextResult,
RejectResult,
RejectSource,
RejectReason,
TransferSyntax,
SopClass,
StorageClass,
UserIdentityType,
} = dcmjsDimse.constants;
class DcmjsDimseScp extends Scp {
constructor(socket, opts) {
super(socket, opts);
this.association = undefined;
}
// Handle incoming association requests
associationRequested(association) {
this.association = association;
// Evaluate calling/called AET and reject association, if needed
if (this.association.getCallingAeTitle() !== 'SCU') {
this.sendAssociationReject(
RejectResult.Permanent,
RejectSource.ServiceUser,
RejectReason.CallingAeNotRecognized
);
return;
}
// Evaluate user identity and reject association, if needed
if (
this.association.getNegotiateUserIdentity() &&
this.association.getUserIdentityPositiveResponseRequested()
) {
if (
this.association.getUserIdentityType() === UserIdentityType.UsernameAndPasscode &&
this.association.getUserIdentityPrimaryField() === 'Username' &&
this.association.getUserIdentitySecondaryField() === 'Password'
) {
this.association.setUserIdentityServerResponse('');
this.association.setNegotiateUserIdentityServerResponse(true);
} else {
this.sendAssociationReject(
RejectResult.Permanent,
RejectSource.ServiceUser,
RejectReason.NoReasonGiven
);
return;
}
}
// Optionally set the preferred max PDU length
this.association.setMaxPduLength(65536);
const contexts = association.getPresentationContexts();
contexts.forEach((c) => {
const context = association.getPresentationContext(c.id);
if (
context.getAbstractSyntaxUid() === SopClass.Verification ||
context.getAbstractSyntaxUid() === SopClass.StudyRootQueryRetrieveInformationModelFind ||
context.getAbstractSyntaxUid() === StorageClass.MrImageStorage
// Accept other presentation contexts, as needed
) {
const transferSyntaxes = context.getTransferSyntaxUids();
transferSyntaxes.forEach((transferSyntax) => {
if (
transferSyntax === TransferSyntax.ImplicitVRLittleEndian ||
transferSyntax === TransferSyntax.ExplicitVRLittleEndian
) {
context.setResult(PresentationContextResult.Accept, transferSyntax);
} else {
context.setResult(PresentationContextResult.RejectTransferSyntaxesNotSupported);
}
});
} else {
context.setResult(PresentationContextResult.RejectAbstractSyntaxNotSupported);
}
});
this.sendAssociationAccept();
}
// Handle incoming C-ECHO requests
cEchoRequest(request, callback) {
const response = CEchoResponse.fromRequest(request);
response.setStatus(Status.Success);
callback(response);
}
// Handle incoming C-FIND requests
cFindRequest(request, callback) {
console.log(request.getDataset());
const pendingResponse = CFindResponse.fromRequest(request);
pendingResponse.setDataset(new Dataset({ PatientID: '12345', PatientName: 'JOHN^DOE' }));
pendingResponse.setStatus(Status.Pending);
const finalResponse = CFindResponse.fromRequest(request);
finalResponse.setStatus(Status.Success);
callback([pendingResponse, finalResponse]);
}
// Handle incoming C-STORE requests
cStoreRequest(request, callback) {
console.log(request.getDataset());
const response = CStoreResponse.fromRequest(request);
response.setStatus(Status.Success);
callback(response);
}
// Handle incoming association release requests
associationReleaseRequested() {
this.sendAssociationReleaseResponse();
}
}
const server = new Server(DcmjsDimseScp);
server.on('networkError', (e) => {
console.log('Network error: ', e);
});
server.listen(port);
// When done
server.close();