Giter Site home page Giter Site logo

bioinformatics-ua / dicoogle Goto Github PK

View Code? Open in Web Editor NEW
416.0 38.0 126.0 25.42 MB

Dicoogle - Open Source PACS

Home Page: http://www.dicoogle.com/

License: GNU General Public License v3.0

Java 80.93% HTML 0.13% JavaScript 17.07% CSS 0.96% Dockerfile 0.02% SCSS 0.88%
dicoogle dicom pacs medical-imaging medical-image-computing medical-informatics metadata java dicoogle-platform javascript

dicoogle's Introduction

Java CI with Maven Build Webapp with Node.js

This is the development branch for Dicoogle 3. See here for the development line of Dicoogle 2, which is being phased out.

Dicoogle is an extensible, platform-independent and open-source PACS archive software that replaces the traditional centralized database with a more agile indexing and retrieval mechanism. It was designed to support automatic extraction, indexing and storage of all meta-data detected in medical images, including private DICOM attribute tags, without re-engineering or reconfiguration requirements.

The architecture of Dicoogle is described in the following articles:

  • Lebre, R., Pinho, E., Jesus, R. , Silva, L.A.B., Costa, C. Dicoogle Open Source: The Establishment of a New Paradigm in Medical Imaging. 2022 Journal of Medical Systems 46: 77. doi:10.1007/s10916-022-01867-3 [link]
  • Lebre, R., Pinho, E., Silva, J.M., Costa, C. Dicoogle Framework for Medical Imaging Teaching and Research. 2020 IEEE Symposium on Computers and Communications (ISCC) [link]
  • Valente, F., Silva, L.A.B., Godinho, T.M., Costa, C. Anatomy of an Extensible Open Source PACS. J Digit Imaging (2016) 29: 284. doi:10.1007/s10278-015-9834-0 [link]

Our official website is at https://www.dicoogle.com. A few essential plugins for Dicoogle are available to download there, as well as a built jar of the Dicoogle platform. To learn how to use Dicoogle, please see our Learning Pack. To build the core platform yourself, please see the section on Building Dicoogle below. The learning pack also has a page on Building Dicoogle.

Brief Documentation

Setup Dicoogle Platform Environment

  1. Copy dicoogle.jar to the installation folder. For example DicoogleDir/

  2. Create the Folder DicoogleDir/Plugins.

    This folder will hold the plugins used by our instance of the Dicoogle Platform.

  3. Next, copy the desired plugins into the DicoogleDir/Plugins Folder.

    The typical setup of Dicoogle involves the deployment of an Indexing and Query Plugin. We supply an implementation of such plugin based in Apache Lucene.

  4. Run Dicoogle.

    Dicoogle may be run as a server: java -jar dicoogle.jar -s

    To load the server and open Dicoogle's user interface with the default browser: java -jar dicoogle.jar

Available Plugins

We provide a few plugins at the official website, in the Downloads page.

  • Lucene Index/Query Plugin - (lucene.jar)

    Plugin Based on Apache Lucene to support indexing and querying of DICOM meta-data. With this plugin set, it is possible to index nearly meta-data and perform free text, keyword-based, and range-based queries.

  • File Storage Plugin - (filestorage.jar)

    Plugin used for the storage of DICOM Files. This plugin is necessary in order to use Dicoogle as a complete DICOM Storage Provider. The core platform provides a fallback implementation which supports reading (but not storing) files from the local file system.

    For storage purposes, our file storage plugin maps the DICOM hierarchical organization (Patient->Study->Series->Image) into a directory tree in the file system. Every object in the Dicoogle Platform may be traced back to its storage location by a URI, similar to file:/tmp/file. In order to support multiple providers, every Storage plugin must define a unique scheme, which maps to the protocol used to store and retrieve content.

    • Settings

      • root-dir: is the root directory where DICOM Files will be stored
      • scheme: Specifies the scheme/protocol of the file plugin. This value is arbitrary, but must be unique among all installed plugins. As such, avoid using well known protocol names such as http or file.

Configuring Plugins

Plugin configurations are accessible via "/DicoogleDir/Plugins/settings/PluginName.xml", where PluginName stands for the name of the plugin. Upon initialization, if no configurations file is supplied, a new one with the default values is created.

Using the Web Application

  • Configuring Services

    In the Management Page, Services and Plugins settings, it is possible to start and/or stop currently running services in real time. Moreover, some configurations like the DICOM service ports may be set.

  • Index a Directory

    Indexing a directory is done simply by accessing the Indexer page, on the side bar. In this page, one can select a root directory to index. The path is a URI defined according to the storage provider, and defaults to the file scheme.

    In the Management pange, one may also enable the Dicoogle Directory Watcher, which creates a daemon that listens for new files in the root directory. After selecting the configurations, the "Apply Settings" button must be pressed. When the right settings are saved, the Start buttons fires the indexing process. Please note that this process may take considerable time to complete.

  • Using the Search Interface

    The search page enables users to execute queries over the indexed meta-data. The query syntax is similar to the Lucene's Tag:Value query format, but free text searches are also supported. For inexperienced users, an advanced input module may also be used.

    In the search interface, it is also possible to select which providers to query. Query providers are actually Query Plugins, that are installed either in the local instance of Dicoogle, or in remote instances if the platform is using the WAN plugin. Therefore, be careful and select exactly which providers you want to query, in order to retrieve more accurate and faster results.

  • Export Results

    After running a query, the result browser shows up, giving the user an intuitive hierarchical view of the results. On this page, there is also an Export button, which is used in order to export the query results into a CSV file. When the export button is clicked, the user has to select which tags (s)he wants to export in the CSV file. This selection is heavily assisted by the interface, on which the user may type an incomplete tag and have presented the available candidates that match the inserted term. Moreover, the text box allows users to copy a list of tags directly from another CSV file, enabling an easier generation of reports.

Using the Web Services

Let us assume that the Web Services for our instance of Dicoogle are running in https://demo.dicoogle.com/

  • Searching Dicoogle provides a flexible web service for querying, under the /search endpoint.

    • Search by Date Range, Access images in date 2005/03/29

      Query: "StudyDate:[20050329 TO 20050329]"

      URL: https://demo.dicoogle.com/search?query=StudyDate:[20050329%20TO%2020050329]

    • Access images in date 2005/03/29 and CT (Computer Tomography) modality

      Query: "Modality:CT AND StudyDate:[20050329 TO 20050329]"

      URL: https://demo.dicoogle.com/search?query=Modality:CT%20AND%20StudyDate:[20050329%20TO%2020050329]

    • Free text search, looking for CT keyword

      Query: CT

      URL: https://demo.dicoogle.com/search?query=CT

  • Access the list of attributes of an image (by SOPInstanceUID)

    URL: https://demo.dicoogle.com/dump?uid=1.3.12.2.1107.5.1.4.54023.30000005032914013107800000965

  • Get a DICOM File

    URL: https://demo.dicoogle.com/legacy/file?uid=1.3.12.2.1107.5.1.4.54023.30000005032914013107800000965

  • Return documents from particular query providers (useful for queries that do not follow the typical Lucene query format)

    URL: https://demo.dicoogle.com/search?query=Modality:NM&provider=lucene&provider=mongo

    Parameters:

    • query : Query String
    • provider: name of the query providers - multiple - optional
      • all: default - asks all available providers.
      • provider name: name of the provider, e.g. lucene.
  • Force Dicoogle to index a given Resource. (useful when conventional notification systems (DICOM Services, DirectoryMonitoring, Human Interface) fail to start the index procedure)

    URL: https://demo.dicoogle.com/management/tasks/index?uri=file:/tmp/dataset-ieeta/

    • Method: POST
    • Parameters:
      • uri: The root identifier of the resources that will be indexed. Please note that Dicoogle will fetch these resources from a storage plugin. Therefore, a plugin capable of handling these resources must be enabled. The provider is identified by the URI's scheme.

A live demo was deployed at the given URL. Feel free to experiment with these services.

We also have programmatic APIs for interfacing with Dicoogle in JavaScript, Java, and Python.

Create your own Plugins

In order to integrate new functionalities in Dicoogle, you may create your own plugin set. A plugin set comprises plugins that are developed with the intent of supporting a given feature, and are packaged in a single jar file for deployment. See the learning pack on Plugin Development for our guide (we also have a wiki page), and our sample plugin project for a base project from which you can start making your own plugins.

Building Dicoogle

Before building, please make sure that your system contains the following tools:

  • Java JDK, either Oracle or OpenJDK (at least version 8);
  • Maven 3;
  1. Retrieve the full source code from this repository: git clone https://github.com/bioinformatics-ua/dicoogle.git
  2. Navigate to the project's base directory, and build the parent Maven project by calling mvn install.
    • Note: this will build the web application using an embedded version of Node.js and npm. To skip building the webapp: mvn install -Dskip.installnodenpm -Dskip.npm
  3. The resulting jar file can be found in "./dicoogle/target".

Contributing

The open source project is maintained by UA.PT Bioinformatics and BMD Software. Your contributions to the software are also welcome. Dicoogle is sought to be useful for R&D and the industry alike. You may find our Development Guidelines in the wiki. Issues containing the easy label should be the most suitable for first open source contributions. For tech support, please prefer contacting the maintainers instead of creating an issue.

Support and consulting

BMD Software

Please contact BMD Software for professional support and consulting services.

Project committers

Maintainers:

  • Luís Bastião (BMD Software - development leader) - @bastiao
  • Eduardo Pinho (BMD Software - co-leader) - @Enet4
  • Rui Lebre (UA.PT Bioinformatics - core, elearning) - @rlebre

Contributors:

Past developers:

  • Carlos Ferreira
  • David Campos
  • Eriksson Monteiro
  • Frederico Silva
  • Frederico Valente
  • Jorge Miguel Silva
  • Leonardo Oliveira
  • Luis Ribeiro
  • Renato Pinho
  • Samuel Campos
  • Tiago Godinho

Project leaders

  • Carlos Costa and José Luis Oliveira (UA.PT Bioinformatics, scientific advisors)
  • Luís Bastião (BMD software - development)

dicoogle's People

Contributors

almeida-a avatar andrealves3 avatar bastiao avatar dependabot[bot] avatar enet4 avatar eriksson avatar fredericojssilva avatar funcionante avatar jorgemfs avatar organom avatar rlebre avatar robobaranik avatar rui-jesus avatar tiberio-baptista avatar tmgodinho avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

dicoogle's Issues

Result list renders redundant React elements

The web page seems to be rendering many redundant React <span> elements when the list of image results is shown.

How to reproduce:

  1. Perform a search with some results;
  2. Select a patient, a study, then a series;
  3. Invisible <div> elements (from the virtual <span>s) are rendered to the page.

screenshot_2015-06-12_16-21-03

API: Extensions to DICOM services

My idea is to extend our SDK to allow to easily do C-MOVE to external servers and DICOM queries.

@tmgodinho what do you think? It will allow to do easy communication with external PACS

[webapp] Logger servlet is hardcoded to a specific file name

We used to write all log entries in Dicoogle to "DICOMLOG.log", but this is no longer true if the logger system is configured to writer to another file (such as what we have right now in "dev"). If the file does not exist, the server will currently fail to process logger requests in this servlet.

To fix this, we can do one of the following (suggestions are welcome):

  • Check all log4j2 appenders in runtime and read the file of the first occurrence of a file appender;
  • Programmatically add an appender (which will always exist regardless of the config file) and use it to retrieve the logs.
  • Enforce all log writing to a specific file, such as "./DICOM.log". I'd preferably avoid this.

I really think this issue should be fixed in 2.0. Poking @fredericojssilva in case he's still working on this.

Dicoogle launches the old GUI client by default.

Given that the GUI client is deprecated, we should also make sure that running the main executable without any arguments does not launch it by default. There are some alternatives:

  • Start the server and open a web browser (if available) on the web application : -w
  • Simply start the server : -s
  • Terminate with an error and enforce the use of the current CLI arguments.

Which one should we choose?

Concurrency problem when fetching storage plugins

WARN servlet.ServletHandler (ServletHandler.java:513) - /dic2png
java.util.ConcurrentModificationException
at java.util.LinkedList$ListItr.checkForComodification(LinkedList.java:966) ~[?:1.8.0_45]
at java.util.LinkedList$ListItr.next(LinkedList.java:888) ~[?:1.8.0_45]
at pt.ua.dicoogle.plugins.PluginController.getStoragePlugins(PluginController.java:272) ~[classes/:?]
at pt.ua.dicoogle.plugins.PluginController.getStorageForSchema(PluginController.java:319) ~[classes/:?]
at pt.ua.dicoogle.server.web.ImageServlet.doGet(ImageServlet.java:117) ~[classes/:?]
at javax.servlet.http.HttpServlet.service(HttpServlet.java:735) ~[dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at javax.servlet.http.HttpServlet.service(HttpServlet.java:848) ~[dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at org.eclipse.jetty.servlet.ServletHolder.handle(ServletHolder.java:681) ~[dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at org.eclipse.jetty.servlet.ServletHandler.doHandle(ServletHandler.java:452) [dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at org.eclipse.jetty.server.session.SessionHandler.doHandle(SessionHandler.java:211) [dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at org.eclipse.jetty.server.handler.ContextHandler.doHandle(ContextHandler.java:1083) [dicoogle-sdk-1.0-SNAPSHOT.jar:?]
at org.eclipse.jetty.servlet.ServletHandler.doScope(ServletHandler.java:379) [dicoogle-sdk-1.0-SNAPSHOT.jar:?]

...

Uniformize Logging

The project is currently relying on multiple logging frameworks, each class appearing to have an independent choice: either java.util.logging or Apache log4j. In addition, slf4j was actually included as a dependency, but barely used in our code.

My suggestion is to adopt slf4j to the entire project and future code, thus being completely abstracted from the underlying logging framework. There is a tool for migrating our current code. I am currently experimenting with it in a separate branch. Meanwhile, I would like to hear your opinions.

Image thumbnail support

We seem to have an implementation of thumbnail generation in the core of Dicoogle, but it is not integrated to indexation/searching procedures. We cannot have thumbnails in our web application unless:

  • indexed images are issued and indexed for thumbnail generation
  • these thumbnails are retrieved when listing a query result.

Search-Webservice: Additional options

These options could be added to the Search service in order to make it more fexible.

  • fields:
    • Select which fields will be returned in the query.
    • The default could be the DICOM DIM fields.

Index-Webservice: Reports and Parameters

  • Reports are not currently beeing return in the service response.
    ** Think they should be returned in a structured manner.
  • Only a single plugin can be specified
    ** It makes more sense to be possible to select a set of plugins.
  • Parameters are not complex at all, just plain strings.
    ** For the sake of coherence, they should be passed as simple parameters, therefore not encoded in json.

Decouple and remove remote GUI

The Remote Swing GUI interface is currently deprecated, and we wish to remove it eventually. Unfortunately, as a result of bad design, some vital features of Dicoogle are unnecessarily coupled with rGUI contents (e.g. server.web.auth.Authentication depends on User-related classes with RMI characteristics).

We should decouple these features from the remote GUI so that it can be safely removed.

Web UI Plugin Interface

With the deprecation of the Swing graphical plugin interface and the uprising of future use cases for Dicoogle, there comes a need for extendability at the web user interface level. Web Service plugins can provide web interfaces, but these are not integrated into the rest of the Dicoogle web application.

Here are some of the features that we are trying to cover:

  • A user wants to perform a query by example (using content-based image retrieval). The best step into performing the query would be dragging and dropping an image into a file upload element in the Search page. The current querying interface is fixed to a basic querying method and an advanced querying method, which lack a means to send images. Future querying engines should be able to expose other query parameters in the interface itself.
  • There may be cases where the querying engine(s) in use affect(s) what contents lie in a result. For instance, a CBIR query operation will provide results with a similarity property, and may not provide the remaining information about the results (such as patient name, patient/study/series ID). On the other hand, there are other interesting ways to show results that might not be covered in the web site, such as showing a grid instead of a list.

Below is a diagram with my proposal. The Dicoogle web page will provide specific UI slots for plugins to be inserted into (multiple plugins in the same slot could be separated with tabs). A Web UI plugin would compose a JavaScript module and a package descriptor (using a "package.json" typically seen in Node.js). An example of a package descriptor can be seen below. At the dicoogle subtree, it must contain at least the file name of the module and a pointer to the slot meant to be attached to.

{
  "name" : "cbir-query",
  "version" : "0.0.1",
  "description" : "CBIR Query-By-Example plugin",
  "dicoogle" : {
    "caption" : "Query by Example",
    "slot-id" : "query",
    "module-file" : "module.js"
  }
}

At the level of the actual module, a DicoogleWeb object would be exposed with some operations only relevant to the web interface. issueQuery would perform the query (thus passing all the data needed by the engine) and trigger a result plugin by invoking an event in the result slot. The onResult event function, implemented by each result web UI plugin, should take a list of results and expose them freely.

webui

Let this issue be used to design and discuss Dicoogle's Web UI plugin interface. I will add more details as more suggestions and ideas come up.

Inconsistency in dump web service

The typical output of the /dump web service (e.g. /dump?uid=1.2.840.113619.2.55.3.680960.718.1352967624.277.5&provider=lucene) would be:

{
  "results": {
    "uri":"file:/some/directory/to/dataset/IMAGE.dcm",
    "fields": {
      "SpecificCharacterSet":"ISO_IR 100\u0000",
      "InstanceNumber":"5.0",
      "StudyID":"1874",
      ...
    }
  },
  "numResults":1,
  "elapsedTime":"NA"
}

However, results becomes an array when the underlying query receives more than one result, which just might happen with multiple providers. /dump?uid=1.2.840.113619.2.55.3.680960.718.1352967624.277.5&provider=lucene&provider=cbir would yield:

{
  "results": [{
    "uri":"file:/some/directory/to/dataset/IMAGE.dcm",
    "fields": {
      "SpecificCharacterSet":"ISO_IR 100\u0000",
      "InstanceNumber":"5.0",
      "StudyID":"1874",
      ...
    }
  },{
    "uri":"file:/a/b/c/img.dcm",
    "fields":{...}
  }],
  "numResults":1,
  "elapsedTime":"NA"
}

This leads to unexpected behaviors in consumer applications. The web application itself is not prepared for this either.

[webapp] RunningIndexTasks not handling tasks properly

The current implementation of RunningIndexingTasks seems to work ok with our Lucene plugin. However, it reveals some flaws when applied to other plugins or simply more than one:

  • When calling index(URI), each indexing provider is given a task of its own. However, these are not assigned a distinct UUID.
  • It is currently not possible to know whether indexing tasks that do not give a task progress have finished. It is expected that their progress value is always -1. The servlet must provide a way to know when such tasks are finished.

Plugins - enable()

I do not believe that the enable method are called to start the Plugin (during the Dicoogle startup)

@tmgodinho it should be called right?

[webapp] ForceIndexing servlet is assuming an IndexReport from index()

The new servlet for forcing the indexing procedure is assuming that all index operations will return an IndexReport. This is currently not guaranteed by the SDK, and for now we must admit that a plain Report might be returned by the indexing plugin.

I have also seen the use of Java reflection to iterate through the report's getters and invoke them to obtain a complete list of entries from the report. Although I understand the concern of supporting a variable number of properties, using Java reflection here is not a good practise: it might retrieve information unrelated to the report (the plugin developer is currently oblivious to Dicoogle's core using reflection in such a manner), and may slightly cripple performance. Later on, version 3.0 will hopefully address this class hierarchy with a redesign of the SDK.

I suggest using a plain instanceof IndexReport for now to identify key cases where an IndexReport is obtained, and interpret a bare Report as "finished indexing".

By the way, as mentioned some time ago, the ForceIndexing servlet should not wait for completion.

Use Jetty with Restlet / JAX-RS / ...?

Ever since we moved to Jetty to host our services, we went back from Restlet to servlet programming, which you know is significantly more frustrating and time consuming.

There is an extension for adding Jetty 9 support to Restlet. I know we do have a bunch of servlets implemented already, but if we can manage to support both servlets and restlet resources under Jetty, what do you say about relying on Restlet again for future WS development?

Export results in the Web Interface

It was reported by one of our users (Milton Santos) that the web user interface fails exporting the results in some datasets. The user feedback was not completed, but it seems that that does not happens and the webservice that exports returns 500 error.

I believe that it is in the core due to the special characters or null values.

Support Restlet attachment instead of Resource in Restlet Web Service Plugins

At the moment, restlet-based plugins are made by implementing a ServerResource and giving it a relative path. However, sometimes it would be more adequate to create a hierarchy of resources from that root, while still taking advantage of Restlet's URI templates. Using a router is the most trivial thing to do:

Router router = new Router(getContext());
router.attach("/items", ItemsResource.class);
router.attach("/items/{itemName}", ItemResource.class);

But right now we cannot attach this router restlet into Dicoogle. This could become critical when implementing services with the likes of WADO-RS, which would be nicely represented with templates (e.g /studies/{StUID}/series/{SeUID}/instances/{InUID}/frames). WADO-RS itself is part of the core, but other developers would prefer to have this.

Restlets are also much more powerful than simple Restlet server resources, allowing developers to create their own converters, for example.

[webapp] Remove online dependencies

The web application's index page is loading some JavaScript libraries (and perhaps other web resources) from CDN's. We should keep all dependencies offline, preferably bundled.

Provide all web services in the same server instance

The main server instance (based on jetty, default port 8080) is currently hosting the web application and all built-in web services, but web services provided by plugins are still being served in another instance (restlet with simple server, default port 6060).

This issue aims to effectively address the matter in #22 and then have all web services in the same server (thus the same port).

Expose unindex a file as a web service.

Expose the un-index feature through the web service. It was available in version 0.5 and now it is not available anymore. It needs to be re-implemented.

Requested by Smirnov Denis.

Stick to one JSON library.

Dicoogle has currently two dependencies (net.sf.json and com.google.gson) that can do the same thing: encode and decode JSON. I may also point out that Gson is nicer to use than the other one. What do you think about sticking to just one dependency?

Plugin Interface improvements

I am a bit worried about how errors should be handled in Dicoogle's plugin interface. For instance, query(String query, Object ... parameters) in the QueryInterface has no throws specification, so there is simply no standardized means of reporting an issue during the execution. A few other methods throw IOException, but not all of them. Furthermore, some new exception types might make more sense here.

How have errors been handled so far? Don't you think we should update these interfaces?

Web - Cannot apply settings in Services and Plugins

When using the web interface, it appears to be impossible to save the "auto-start" configuration. When moving to another tab and returning to this one, the previous modifications to these checkboxes are gone.

Handle CORS properly

Many of our servlets are currently accepting all origins, which is not safe. This should be carefully reconsidered, and we may start by removing all "Access-Control-Allow-Origin" header assignments in the servlets.

Search-WebService: Trailing empty characters

It would be better to remove trailing character from the search webservice response.
Example:

  • "StudyInstanceUID": "1.3.12.2.1107.5.6.1.123.24412.0.231616614823159\u0000\u0000\u0000\u0000\u0000",«
  • "SeriesInstanceUID": "1.3.12.2.1107.5.6.1.123.24412.0.231737174002313\u0000\u0000\u0000\u0000\u0000",
  • "SOPInstanceUID": "1.3.12.2.1107.5.6.1.123.24412.0.231019730551383\u0000\u0000\u0000\u0000\u0000"

Default query provider

Back in #11 it was explained why there shouldn't be a way to query all providers. How about we support configuring a default (or recommended) query provider instead? This holds the advantage that clients do not need to specify a provider for making simple searches, given that in many cases, only one provider is available anyway.

Endpoints for specific UI features

In order to create a flexibility of integrate the interface with third-party modules, I'm suggesting to support three end-points with direct access to the UI (something like that) :

  • ui/search?query=
  • ui/image?SOPInstanceUID=
  • ui/dump?SOPInstanceUID=

[webapp] Advanced Search button is not responsive

The "Advanced" button in the search view behaves as expected, but it does not make clear to the user that clicking again reverts the search to a basic search. So I suggest that clicking this button should toggle between the captions "Advanced" and "Basic".

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    🖖 Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. 📊📈🎉

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google ❤️ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.