765. EPMO Open Source Coordination Office Redaction File Detail Report

Produced by Araxis Merge on 10/18/2018 2:02:18 PM Central Daylight Time. See www.araxis.com for information about Merge. This report uses XHTML and CSS2, and is best viewed with a modern standards-compliant browser. For optimum results when printing this report, use landscape orientation and enable printing of background images and colours in your browser.

765.1 Files compared

# Location File Last Modified
1 VIX_SIV_v3_0_patch_201_build_8.zip\v3.0_patch_201_build_8\VISA\Java\ImageConversion\main\src\java\gov\va\med\imaging\conversion ImageConversionUtility.java Thu Oct 11 13:30:10 2018 UTC
2 VIX_SIV_v3_0_patch_201_build_8.zip\v3.0_patch_201_build_8\VISA\Java\ImageConversion\main\src\java\gov\va\med\imaging\conversion ImageConversionUtility.java Wed Oct 17 18:50:21 2018 UTC

765.2 Comparison summary

Description Between
Files 1 and 2
Text Blocks Lines
Unchanged 4 2226
Changed 3 6
Inserted 0 0
Removed 0 0

765.3 Comparison options

Whitespace
Character case Differences in character case are significant
Line endings Differences in line endings (CR and LF characters) are ignored
CR/LF characters Not shown in the comparison detail

765.4 Active regular expressions

No regular expressions were active.

765.5 Comparison detail

  1   /**
  2    * 
  3     Package:  MAG - Vis tA Imaging
  4     WARNING:  Per VHA D irective 2 004-038, t his routin e should n ot be modi fied.
  5     Date Cre ated: May  2, 2008
  6     Site Nam e:  Washin gton OI Fi eld Office , Silver S pring, MD
  7       Developer:     PI I
  8     Descript ion: 
  9  
  10           ;;  +-------- ---------- ---------- ---------- ---------- ---------- ---------- +
  11           ;;  Property  of the US  Government .
  12           ;;  No permis sion to co py or redi stribute t his softwa re is give n.
  13           ;;  Use of un released v ersions of  this soft ware requi res the us er
  14           ;;   to execu te a writt en test ag reement wi th the Vis tA Imaging
  15           ;;   Developm ent Office  of the De partment o f Veterans  Affairs,
  16           ;;   telephon e (301) 73 4-0100.
  17           ;;
  18           ;;  The Food  and Drug A dministrat ion classi fies this  software a s
  19           ;;  a Class I I medical  device.  A s such, it  may not b e changed
  20           ;;  in any wa y.  Modifi cations to  this soft ware may r esult in a n
  21           ;;  adulterat ed medical  device un der 21CFR8 20, the us e of which
  22           ;;  is consid ered to be  a violati on of US F ederal Sta tutes.
  23           ;;  +-------- ---------- ---------- ---------- ---------- ---------- ---------- +
  24  
  25    */
  26   package go v.va.med.i maging.con version;
  27  
  28   import gov .va.med.im aging.Stri ngUtil;
  29   import gov .va.med.im aging.conv ersion.enu ms.ImageCo nversionSa tisfaction ;
  30   import gov .va.med.im aging.core .interface s.IImageCo nversionCo nfiguratio n;
  31   import gov .va.med.im aging.core .interface s.ImageSto rageFacade ;
  32   import gov .va.med.im aging.core .interface s.StorageC redentials ;
  33   import gov .va.med.im aging.core .interface s.exceptio ns.Connect ionExcepti on;
  34   import gov .va.med.im aging.core .interface s.exceptio ns.ImageCo nversionEx ception;
  35   import gov .va.med.im aging.core .interface s.exceptio ns.ImageNe arLineExce ption;
  36   import gov .va.med.im aging.core .interface s.exceptio ns.ImageNo tFoundExce ption;
  37   import gov .va.med.im aging.core .interface s.exceptio ns.MethodE xception;
  38   import gov .va.med.im aging.exch ange.busin ess.ImageF ormatAllow ableConver sionList;
  39   import gov .va.med.im aging.exch ange.busin ess.ImageF ormatQuali ty;
  40   import gov .va.med.im aging.exch ange.busin ess.ImageF ormatQuali tyList;
  41   import gov .va.med.im aging.exch ange.busin ess.ImageS treamRespo nse;
  42   import gov .va.med.im aging.exch ange.conve rsion.exce ptions.Ima geConversi onCompress ionExcepti on;
  43   import gov .va.med.im aging.exch ange.conve rsion.exce ptions.Ima geConversi onDecompre ssionExcep tion;
  44   import gov .va.med.im aging.exch ange.conve rsion.exce ptions.Ima geConversi onIOExcept ion;
  45   import gov .va.med.im aging.exch ange.conve rsion.exce ptions.Ima geConversi onInvalidI nputExcept ion;
  46   import gov .va.med.im aging.exch ange.conve rsion.inte rfaces.IIm ageConvers ion;
  47   import gov .va.med.im aging.exch ange.enums .ImageForm at;
  48   import gov .va.med.im aging.exch ange.enums .ImageQual ity;
  49   import gov .va.med.im aging.exch ange.enums .StoragePr oximity;
  50   import gov .va.med.im aging.exch ange.stora ge.ByteBuf ferBackedI mageInputS tream;
  51   import gov .va.med.im aging.exch ange.stora ge.ByteBuf ferBackedI mageStream Response;
  52   import gov .va.med.im aging.exch ange.stora ge.ByteBuf ferBackedI nputStream ;
  53   import gov .va.med.im aging.exch ange.stora ge.ByteBuf ferBackedO bject;
  54   import gov .va.med.im aging.tran sactioncon text.Trans actionCont ext;
  55   import gov .va.med.im aging.tran sactioncon text.Trans actionCont extFactory ;
  56  
  57   import jav a.io.Buffe redReader;
  58   import jav a.io.IOExc eption;
  59   import jav a.io.Input Stream;
  60   import jav a.io.Input StreamRead er;
  61   import jav a.io.Seque nceInputSt ream;
  62   import jav a.util.Has hMap;
  63   import jav a.util.Ite rator;
  64   import jav a.util.Lis t;
  65   import jav a.util.Map ;
  66   import jav a.util.Map .Entry;
  67   import jav a.util.Set ;
  68  
  69   import org .apache.co mmons.io.I OUtils;
  70   import org .apache.lo gging.log4 j.LogManag er;
  71   import org .apache.lo gging.log4 j.Logger;
  72  
  73   /**
  74    * Image c onversion  utility do es the wor k of deter mining wha t the stor ed image t ype is, wh at
  75    * it can  be convert ed into an d then act ually call ing the im age conver sion metho ds to 
  76    * convert  the image
  77    * 
  78    * @author   PI I
  79    *
  80    */
  81   public cla ss ImageCo nversionUt ility 
  82   {
  83           pr ivate fina l static L ogger logg er = LogMa nager.getL ogger(Imag eConversio nUtility.c lass);
  84           pr ivate fina l ImageSto rageFacade  storageFa cade;
  85           pr ivate fina l ImageCon versionSat isfaction  conversion Satisfacti on;
  86           pr ivate fina l boolean  updateDico mHeaders;
  87  
  88           /* *
  89            *  Create a  new image  conversion  utility f or convert ing a stor ed image i nto the fo rmat reque sted by th e user
  90            *  
  91            *  @param im ageStorage Facade The  storage f acade know s how to o pen the fi le needed.
  92            *  @param co nversionSa tisfaction  Image con version sa tisfaction  level for  this imag e conversi on utility
  93            *  @param up dateDicomH eaders Det ermines if  the DICOM  header sh ould be up dated for  images tha t are stor ed in DICO M
  94            * /
  95           pu blic Image Conversion Utility(Im ageStorage Facade ima geStorageF acade, 
  96                             ImageC onversionS atisfactio n conversi onSatisfac tion,
  97                             boolea n updateDi comHeaders )
  98           {
  99                    supe r();
  100                    this .storageFa cade = ima geStorageF acade;
  101                    this .conversio nSatisfact ion = conv ersionSati sfaction;
  102                    this .updateDic omHeaders  = updateDi comHeaders ;
  103           }
  104  
  105           pr ivate IIma geConversi on getImag eConversio n()
  106           {
  107                    retu rn ImageCo nversionFa ctory.getI mageConver sion();
  108           }
  109  
  110           pr ivate IIma geConversi onConfigur ation getI mageConfig uration()
  111           {
  112                    retu rn ImageCo nversionFa ctory.getI mageConver sionConfig uration();
  113           }
  114           
  115           /* *
  116            *  Retrieves  the image  from the  list of fi le paths u sing the s pecified f ormat qual ity list a nd credent ials
  117            *  @param fi les
  118            *  @param re questForma tQualityLi st The lis t of file  formats to  use when  requesting  the image
  119            *  @param co nvertForma tQualityLi st The lis t of file  formats th e image ca n be retur ned 
  120            *       in -  if the im age is req uested in  a format n ot include d in this  list, then  the image  must be c onverted
  121            *  @param tx tFileAvail able This  determines  if the im age conver sion will  attempt to  download  the TXT fi le, this v alue 
  122            *       has  no impact  if the TXT  file is n ecessary t o generate  a DICOM i mage. This  is only u sed if the  TXT file  might be 
  123            *       incl uded in th e result ( not for co nversion)
  124            *  @return A  stream to  the opene d image
  125            *  @throws I mageNearLi neExceptio n
  126            *  @throws I mageNotFou ndExceptio n
  127            *  @throws I mageConver sionExcept ion
  128            *  @throws C onnectionE xception
  129            * /
  130           pu blic Image StreamResp onse getIm age(List<I mageConver sionFilePa th> files,  
  131                             ImageF ormatQuali tyList req uestFormat QualityLis t, 
  132                             ImageF ormatQuali tyList con vertFormat QualityLis t,
  133                             boolea n txtFileA vailable)
  134           th rows Image NearLineEx ception, I mageNotFou ndExceptio n, ImageCo nversionEx ception,
  135           Co nnectionEx ception, M ethodExcep tion
  136           {
  137                    retu rn getImag e(files, r equestForm atQualityL ist, conve rtFormatQu alityList,
  138                                      txtFileA vailable,  null);
  139           }
  140  
  141           /* *
  142            *  Retrieves  the image  from the  list of fi le paths u sing the s pecified f ormat qual ity list a nd credent ials
  143            *  @param fi les
  144            *  @param re questForma tQualityLi st The lis t of file  formats to  use when  requesting  the image
  145            *  @param co nvertForma tQualityLi st The lis t of file  formats th e image ca n be retur ned 
  146            *       in -  if the im age is req uested in  a format n ot include d in this  list, then  the image  must be c onverted
  147            *  @param tx tFileAvail able This  determines  if the im age conver sion will  attempt to  download  the TXT fi le, this v alue 
  148            *       has  no impact  if the TXT  file is n ecessary t o generate  a DICOM i mage. This  is only u sed if the  TXT file  might be 
  149            *       incl uded in th e result ( not for co nversion)
  150            *  @param st orageCrede ntials The  credentia ls used to  access th e storage  device for  the files
  151            *  @return A  stream to  the opene d image
  152            *  @throws I mageNearLi neExceptio n
  153            *  @throws I mageNotFou ndExceptio n
  154            *  @throws I mageConver sionExcept ion
  155            *  @throws C onnectionE xception
  156            * /
  157           pu blic Image StreamResp onse getIm age(List<I mageConver sionFilePa th> files,  
  158                             ImageF ormatQuali tyList req uestFormat QualityLis t, 
  159                             ImageF ormatQuali tyList con vertFormat QualityLis t,
  160                             boolea n txtFileA vailable,
  161                             Storag eCredentia ls storage Credential s)
  162           th rows Image NearLineEx ception, I mageNotFou ndExceptio n, ImageCo nversionEx ception,
  163           Co nnectionEx ception, M ethodExcep tion
  164           {
  165                    retu rn getImag e(files, r equestForm atQualityL ist, conve rtFormatQu alityList,
  166                                      txtFileA vailable,  storageCre dentials,  null);
  167           }
  168  
  169           /* *
  170            *  Retrieves  the image  from the  list of fi le paths u sing the s pecified f ormat qual ity list a nd credent ials
  171            *  @param fi les
  172            *  @param re questForma tQualityLi st The lis t of file  formats to  use when  requesting  the image
  173            *  @param co nvertForma tQualityLi st The lis t of file  formats th e image ca n be retur ned 
  174            *       in -  if the im age is req uested in  a format n ot include d in this  list, then  the image  must be c onverted
  175            *  @param tx tFileAvail able This  determines  if the im age conver sion will  attempt to  download  the TXT fi le, this v alue 
  176            *       has  no impact  if the TXT  file is n ecessary t o generate  a DICOM i mage. This  is only u sed if the  TXT file  might be 
  177            *       incl uded in th e result ( not for co nversion)
  178            *  @param st orageCrede ntials The  credentia ls used to  access th e storage  device for  the files
  179            *  @param hi sUpdate Th e HIS upda te from th e database
  180            *  @return
  181            *  @throws I mageNearLi neExceptio n
  182            *  @throws I mageNotFou ndExceptio n
  183            *  @throws I mageConver sionExcept ion
  184            *  @throws C onnectionE xception
  185            * /
  186           pu blic Image StreamResp onse getIm age(List<I mageConver sionFilePa th> files,  
  187                             ImageF ormatQuali tyList req uestFormat QualityLis t,
  188                             ImageF ormatQuali tyList con vertFormat QualityLis t,
  189                             boolea n txtFileA vailable,
  190                             Storag eCredentia ls storage Credential s, HashMap <String, S tring> his Update)
  191           th rows Image NearLineEx ception, I mageNotFou ndExceptio n, ImageCo nversionEx ception, 
  192           Co nnectionEx ception, M ethodExcep tion
  193           {
  194                    try
  195                    {
  196                             for(Im ageConvers ionFilePat h filePath  : files)
  197                             {
  198                                      ImageStr eamRespons e response  = retriev eAndCompre ssImage(fi lePath, 
  199                                                       re questForma tQualityLi st, conver tFormatQua lityList,
  200                                                       tx tFileAvail able, stor ageCredent ials, hisU pdate);
  201                                      if(respo nse != nul l)
  202                                               return res ponse;
  203                             }
  204                             return  null;
  205                    }
  206                    fina lly
  207                    {
  208                             if(sto rageFacade  != null)
  209                             {
  210                                      // be su re to clea r the buff ers when d one with t he convers ion (alway s clear th em)
  211                                      storageF acade.clea rBuffers() ;
  212                             }
  213                    }
  214           }
  215  
  216           pr ivate Imag eStreamRes ponse retr ieveAndCom pressImage (ImageConv ersionFile Path fileP ath, 
  217                             ImageF ormatQuali tyList req uestFormat QualityLis t, 
  218                             ImageF ormatQuali tyList con vertFormat QualityLis t,
  219                             boolea n txtFileA vailable,
  220                             Storag eCredentia ls storage Credential s, HashMap <String, S tring> his Update)
  221           th rows Image NearLineEx ception, I mageNotFou ndExceptio n, ImageCo nversionEx ception, 
  222           Co nnectionEx ception, M ethodExcep tion
  223           {
  224                    // j ust to be  sure every thing is c lean
  225                    //re turnBuffer s();
  226                    Byte BufferBack edImageStr eamRespons e response  = null;
  227                    try 
  228                    {
  229                             String  imageFile name = fil ePath.getF ilePath();
  230                             logger .info("Ope ning input  stream to  image ["  + imageFil ename + "] ");
  231  
  232                             if(ima geFilename .startsWit h("."))
  233                             {
  234                                      logger.e rror("Imag e starts w ith a '.',  cannot ac cess or re trieve can ned images  from acce lerator");
  235                                      return n ull;
  236                             }
  237                             Transa ctionConte xt transac tionContex t = Transa ctionConte xtFactory. get();
  238                             transa ctionConte xt.addDebu gInformati on("Openin g image wi th path '"  + imageFi lename + " '.");
  239                             respon se = stora geFacade.o penImageSt ream(image Filename, 
  240                                               storageCre dentials,  filePath.g etStorageP roximity() , requestF ormatQuali tyList);
  241           
  242                             if (re sponse.get FilePath()  == null)
  243                             {
  244                                      if ((fil ePath != n ull) && (f ilePath.ge tFilePath( ) != null) )
  245                                               response.s etFilePath (filePath. getFilePat h());
  246                             }
  247                             
  248                             if (re sponse.get StorageUse rname() ==  null)
  249                             {
  250                                      if ((sto rageCreden tials != n ull) && (s torageCred entials.ge tUsername( ) != null) )
  251                                               response.s etStorageS iteNumber( storageCre dentials.g etUsername ());
  252                             }
  253                             
  254                             if (re sponse.get StoragePas sword() ==  null)
  255                             {
  256                                      if ((sto rageCreden tials != n ull) && (s torageCred entials.ge tPassword( ) != null) )
  257                                               response.s etStorageP assword(st orageCrede ntials.get Password() );
  258                             }
  259                             
  260                             ImageF ormat stor edFormat =  response. getImageFo rmat();
  261                             
  262                             ImageQ uality sto redQuality  = respons e.getImage Quality();
  263                             if(sto redQuality  == null)
  264                                      storedQu ality = fi lePath.get ImageQuali ty();
  265                             if(res ponse.getI mageQualit y() == nul l)
  266                                      response .setImageQ uality(sto redQuality );                          
  267                             
  268                             if(sto redFormat  != null)
  269                             {
  270                                      transact ionContext .setDataSo urceImageF ormatRecei ved(stored Format.toS tring());
  271                             }
  272                             if(sto redQuality  != null)
  273                             {
  274                                      transact ionContext .setDataSo urceImageQ ualityRece ived(store dQuality.t oString()) ;
  275                             }
  276  
  277                             logger .debug("st oredFormat : " + stor edFormat);
  278                             
  279                             // spe cial case  if we can' t determin e the form at of the  file, just  want to r eturn it i f allowed
  280                             if(sto redFormat  == ImageFo rmat.ORIGI NAL)
  281                             {
  282                                      logger.i nfo("Unabl e to deter mine the f ormat of f ile [" + i mageFilena me + "]");
  283                                      if(reque stAllowsOr iginalImag eType(conv ertFormatQ ualityList ))
  284                                      {
  285                                               logger.inf o("Unknown  format is  allowed b ecause [OR IGINAL] is  in reques t, returni ng ORIGINA L image fo rmat");
  286                                               // want to  set the i mage quali ty in the  response a lso...
  287                                               // do anyt hing speci al if inco rrect imag e quality?  probably  can't!
  288                                               if(respons e.getImage Quality()  == null)
  289                                                       re sponse.set ImageQuali ty(storedQ uality);
  290                                               if((stored Quality !=  ImageQual ity.THUMBN AIL) &&
  291                                                                (res ponse.getT xtStream()  == null)  && (!Image Format.isD ICOMFormat (response. getImageFo rmat()))
  292                                                                && ( txtFileAva ilable))
  293                                               {
  294                                                       By teBufferBa ckedInputS tream txtS tream = 
  295                                                                getT xtStreamHa ndleExcept ion(imageF ilename, s torageCred entials, h isUpdate);
  296                                                       re sponse.set TxtStream( txtStream) ;
  297                                                       //  can't do  the DICOM  header upd ate since  we don't k now what t he format  of the ima ge is
  298                                               }
  299                                               return res ponse;
  300                                      }
  301                                      logger.d ebug("requ estAllowsO riginalIma geType ret urned Fals e.");
  302                             }
  303                             
  304                             if(isS toredForma tInRequest (requestFo rmatQualit yList, sto redFormat)  
  305                                               && storedQ uality ==  ImageQuali ty.DIAGNOS TICUNCOMPR ESSED){
  306                                      
  307                                      logger.i nfo("Deter mined stor ed Format  [" + store dFormat +
  308                                                       "]  matches a nd image q uality is  100. Passi ng image \ "as is\"." );
  309                                      if(respo nse.getIma geQuality( ) == null)
  310                                               response.s etImageQua lity(store dQuality);
  311                                      if(store dQuality ! = ImageQua lity.THUMB NAIL)
  312                                      {
  313                                               setImageSt reamRespon seTextFile IfNecessar y(response , storedFo rmat, imag eFilename,  
  314                                                                stor ageCredent ials, hisU pdate, txt FileAvaila ble);                                           
  315                                               if((ImageF ormat.isDI COMFormat( storedForm at)) && (u pdateDicom Headers))
  316                                               {
  317                                                       //  if DICOM  then try t o update t he DICOM h eader with  the lates t values
  318                                                       re turn updat eDICOMHead erHandleEx ceptions(r esponse, s toredForma t, storedQ uality);
  319                                               }
  320                                      }
  321                                      return r esponse;                                   
  322                             }
  323  
  324                             Iterat or<ImageFo rmatQualit y> qualiti esIterator  = convert FormatQual ityList.it erator();
  325                             boolea n canCompr essStoredF ormat = ca nCompressF ormat(stor edFormat);
  326                             logger .debug("ca nCompressS toredForma t returned  " + canCo mpressStor edFormat);
  327  
  328  
  329                             // if  satisfy to p request  is false t hen try to  just retu rn the out put if pos sible
  330                             // we  would want  to just r eturn the  data witho ut convert ing it if  it matches  the 
  331                             // req uested for mats
  332                             //if(! isSatisfyT opRequest( ))
  333                             if(con versionSat isfaction  == ImageCo nversionSa tisfaction .SATISFY_A NY_REQUEST )
  334                             {
  335                                      logger.i nfo("Check ing to see  if image  in format  [" + store dFormat +  "] can be  returned i n current  format");
  336                                      if(isSto redFormatI nRequest(c onvertForm atQualityL ist, store dFormat, s toredQuali ty))
  337                                      {
  338                                               logger.inf o("Image i n format [ " + stored Format + " ] and can  be returne d in this  format, re turning");
  339                                               if(respons e.getImage Quality()  == null)
  340                                                       re sponse.set ImageQuali ty(storedQ uality);
  341                                               if(storedQ uality !=  ImageQuali ty.THUMBNA IL)
  342                                               {
  343                                                       se tImageStre amResponse TextFileIf Necessary( response,  storedForm at, imageF ilename, 
  344                                                                         storag eCredentia ls, hisUpd ate, txtFi leAvailabl e);                                           
  345                                                       if ((ImageFor mat.isDICO MFormat(st oredFormat )) && (upd ateDicomHe aders))
  346                                                       {
  347                                                                // i f DICOM th en try to  update the  DICOM hea der with t he latest  values
  348                                                                retu rn updateD ICOMHeader HandleExce ptions(res ponse, sto redFormat,  storedQua lity);
  349                                                       }
  350                                               }
  351                                               return res ponse;
  352                                      }
  353                             }
  354                             else i f(conversi onSatisfac tion == Im ageConvers ionSatisfa ction.SATI SFY_ALLOWE D_COMPRESS ION)
  355                             {
  356                                      // if th e image is  stored in  a compres sed format  and that  format is  in the req uested for mat list
  357                                      // then  the image  can be ret urned rega rdless of  where it i s in the l ist.
  358                                      if(store dFormat.is Compressed ())
  359                                      {
  360                                               logger.inf o("Image i s stored i n format [ " + stored Format + " ] which is  compresse d, checkin g to see i f image ca n be retur ned in thi s format") ;
  361                                               if(isStore dFormatInR equest(con vertFormat QualityLis t, storedF ormat, sto redQuality ))
  362                                               {
  363                                                       lo gger.info( "Image in  format ["  + storedFo rmat + "]  and can be  returned  in this fo rmat, retu rning");
  364                                                       if (response. getImageQu ality() ==  null)
  365                                                                resp onse.setIm ageQuality (storedQua lity);
  366                                                       if (storedQua lity != Im ageQuality .THUMBNAIL )
  367                                                       {
  368                                                                setI mageStream ResponseTe xtFileIfNe cessary(re sponse, st oredFormat
  369                                                                                  imageFil ename, sto rageCreden tials, his Update, tx tFileAvail able);                                            
  370                                                                if(( ImageForma t.isDICOMF ormat(stor edFormat))  && (updat eDicomHead ers))
  371                                                                {
  372                                                                         // if  DICOM then  try to up date the D ICOM heade r with the  latest va lues
  373                                                                         return  updateDIC OMHeaderHa ndleExcept ions(respo nse, store dFormat, s toredQuali ty);
  374                                                                }
  375                                                       }
  376                                                       re turn respo nse;
  377                                               }
  378                                      }
  379                             }
  380                             ImageF ormatQuali ty quality  = getNext AllowableI mageFormat Quality(st oredFormat , qualitie sIterator) ;
  381                             
  382                             while( quality !=  null)
  383                             {
  384                                      logger.i nfo("Attem pting to g enerate im age of typ e '" + qua lity.getIm ageFormat( ) + "'.");
  385                                      if(((sto redFormat  == quality .getImageF ormat()) |
  386                                                       (q uality.get ImageForma t() == Ima geFormat.O RIGINAL))
  387                                                       &&  ((storedQ uality ==  quality.ge tImageQual ity()) || 
  388                                                                         (!canC ompressSto redFormat) ))
  389                                      {
  390                                               logger.inf o("Image f ormat [" +  storedFor mat + "] m atches req uest forma t, returni ng image") ;
  391                                               if(respons e.getImage Quality()  == null)
  392                                                       re sponse.set ImageQuali ty(quality .getImageQ uality());
  393                                               if(quality .getImageQ uality() ! = ImageQua lity.THUMB NAIL)
  394                                               {
  395                                                       se tImageStre amResponse TextFileIf Necessary( response,  storedForm at, 
  396                                                                         imageF ilename, s torageCred entials, h isUpdate,  txtFileAva ilable);                                            
  397                                                       if ((ImageFor mat.isDICO MFormat(st oredFormat )) && (upd ateDicomHe aders))
  398                                                       {
  399                                                                // i f DICOM th en try to  update the  DICOM hea der with t he latest  values
  400                                                                retu rn updateD ICOMHeader HandleExce ptions(res ponse, sto redFormat,  storedQua lity);
  401                                                       }
  402                                               }
  403                                               return res ponse;
  404                                      }       
  405  
  406                                      // if th e original  file type  is not in  the right  quality b ut the cur rent conve rsion
  407                                      // is "o riginal",  then just  return wha t we have.  Original  should alw ays happen  last
  408                                      // so th is is a la st resort  and the us er said th ey could h andle the  original f ormat
  409                                      if(quali ty.getImag eFormat()  == ImageFo rmat.ORIGI NAL)
  410                                      {
  411                                               logger.inf o("Image i s in forma t [" + sto redFormat  + "] and [ ORIGINAL]  can be ret urned, ret urning sto red image" );
  412                                               if(respons e.getImage Quality()  == null)
  413                                                       re sponse.set ImageQuali ty(storedQ uality);
  414                                               if(quality .getImageQ uality() ! = ImageQua lity.THUMB NAIL)
  415                                               {
  416                                                       se tImageStre amResponse TextFileIf Necessary( response,  storedForm at, imageF ilename, 
  417                                                                         storag eCredentia ls, hisUpd ate, txtFi leAvailabl e);                                                                                       
  418                                                       if ((ImageFor mat.isDICO MFormat(st oredFormat )) && (upd ateDicomHe aders))
  419                                                       {
  420                                                                // i f DICOM th en try to  update the  DICOM hea der with t he latest  values
  421                                                                retu rn updateD ICOMHeader HandleExce ptions(res ponse, sto redFormat,  storedQua lity);
  422                                                       }
  423                                               }
  424                                               return res ponse;
  425                                      }
  426  
  427                                      // if we  get to he re, we hav e to do a  conversion , put it i nto the bu ffer?
  428                                      
  429                                      // at th is point w e know we  need to do  some conv ersion, so  make sure  the image  
  430                                      // is in  a buffer  in case we  need to r euse it.
  431                                      
  432                                      // no lo nger need  to put int o buffer,  will be ha ndled inte rnally (ri ght?)
  433                                      
  434                                      //respon se = stora geFacade.p utStreamIn toBuffer(i mageFilena me, respon se);         
  435                                      
  436  
  437                                      logger.i nfo("Able  to convert  from [" +  storedFor mat + "] t o [" + qua lity.getIm ageFormat( ) + "]");
  438                                      transact ionContext .addDebugI nformation ("Converti ng from '"  + storedF ormat + "'  to '" + q uality.get ImageForma t() + "'." );
  439                                      try
  440                                      {
  441                                               // if requ ested qual ity format  is DICOM  then we ne ed the TXT  file befo re we call  compress  and conver t (to buil d the head er)
  442                                               if(ImageFo rmat.isDIC OMFormat(q uality.get ImageForma t()))
  443                                               {
  444                                                       if (isDecompr ess(stored Format, qu ality.getI mageFormat ()))
  445                                                       {
  446                                                                Imag eStreamRes ponse conv ertedRespo nse = deco mpressImag e(response , quality) ;
  447                                                                if(c onvertedRe sponse !=  null)
  448                                                                {
  449                                                                         return  converted Response;
  450                                                                }
  451                                                       }
  452                                                       el se
  453                                                       {
  454                                                                // d o conversi on
  455                                                                if(r esponse.ge tTxtStream () == null )
  456                                                                {
  457                                                                         ByteBu fferBacked InputStrea m txtStrea m = 
  458                                                                                  getTxtSt reamHandle Exception( imageFilen ame, stora geCredenti als, hisUp date);
  459                                                                         respon se.setTxtS tream(txtS tream);
  460                                                                }
  461                                                                Imag eStreamRes ponse conv ertedRespo nse = comp ressAndCon vertImage( response,  quality);
  462                                                                if(c onvertedRe sponse !=  null)
  463                                                                {
  464                                                                         return  converted Response;
  465                                                                }
  466                                                       }
  467                                               }
  468                                               else
  469                                               {
  470                                                       //  check to  see if sho uld do a d ecompressi on rather  than compr ession
  471                                                       if (isDecompr ess(stored Format, qu ality.getI mageFormat ()))
  472                                                       {
  473                                                                // n ot creatin g a DICOM  file so on ly doing c ompression , return T XT file af ter making  the image
  474                                                                Imag eStreamRes ponse conv ertedRespo nse = deco mpressImag e(response , quality) ;
  475                                                                if(c onvertedRe sponse !=  null)
  476                                                                {
  477                                                                         if((qu ality.getI mageQualit y() != Ima geQuality. THUMBNAIL)
  478                                                                                           && (conver tedRespons e.getTxtSt ream() ==  null)
  479                                                                                           && (!Image Format.isD ICOMFormat (response. getImageFo rmat())))
  480                                                                         {
  481                                                                                  ByteBuff erBackedIn putStream  txtStream 
  482                                                                                           getTxtStre amHandleEx ception(im ageFilenam e, storage Credential s, hisUpda te);
  483                                                                                  converte dResponse. setTxtStre am(txtStre am);
  484                                                                         }
  485                                                                         return  converted Response;
  486                                                                }
  487                                                       }
  488                                                       el se
  489                                                       {                                                             
  490                                                                Stri ng modalit y = null;
  491                                                                // o nly get th e modality  if the re quested qu ality is n ot thumbna il
  492                                                                if(q uality.get ImageQuali ty() != Im ageQuality .THUMBNAIL )
  493                                                                {
  494                                                                         // get  modality  code from  TXT file f or non-DIC OM compres sion
  495                                                                         ByteBu fferBacked InputStrea m txtStrea m = respon se.getTxtS tream();
  496                                                                         if(txt Stream ==  null)
  497                                                                                  txtStrea m = getTxt StreamHand leExceptio n(imageFil ename, sto rageCreden tials, his Update);
  498                                                                         modali ty = getTX TModality( txtStream) ; // get m odality co de and clo se partial ly consume d stream!
  499                                                                }
  500                                                                // n ot creatin g a DICOM  file so on ly doing c ompression , return T XT file af ter making  the image
  501                                                                Imag eStreamRes ponse conv ertedRespo nse = comp ressImage( imageFilen ame, respo nse, quali ty, modali ty);
  502                                                                if(c onvertedRe sponse !=  null)
  503                                                                {
  504                                                                         if((qu ality.getI mageQualit y() != Ima geQuality. THUMBNAIL)
  505                                                                                           && (conver tedRespons e.getTxtSt ream() ==  null)
  506                                                                                           && (!Image Format.isD ICOMFormat (response. getImageFo rmat()))
  507                                                                                           && (txtFil eAvailable ))
  508                                                                         {
  509                                                                                  ByteBuff erBackedIn putStream  txtStream 
  510                                                                                           getTxtStre amHandleEx ception(im ageFilenam e, storage Credential s, hisUpda te);
  511                                                                                  converte dResponse. setTxtStre am(txtStre am);
  512                                                                         }
  513                                                                         return  converted Response;
  514                                                                }
  515                                                       }
  516                                               }
  517                                      }
  518                                      catch(Im ageConvers ionDecompr essionExce ption icdX )
  519                                      {
  520                                               logger.err or("Decomp ression er ror during  convertin g image ["  + imageFi lename + " ]", icdX);
  521                                               transactio nContext.a ddDebugInf ormation(" ImageConve rsionDecom pressionEx ception co nverting i mage, " +  icdX.getMe ssage() +  ".");
  522                                      }
  523                                      catch(Im ageConvers ionCompres sionExcept ion iccX)
  524                                      {
  525                                               logger.err or("Compre ssion erro r during c onverting  image [" +  imageFile name + "]" , iccX);
  526                                               transactio nContext.a ddDebugInf ormation(" ImageConve rsionCompr essionExce ption conv erting ima ge, " + ic cX.getMess age() + ". ");
  527                                      }
  528                                      catch(Im ageConvers ionIOExcep tion icioX )
  529                                      {
  530                                               logger.err or("IO err or during  converting  image ["  + imageFil ename + "] ", icioX);
  531                                               transactio nContext.a ddDebugInf ormation(" ImageConve rsionIOExc eption con verting im age, " + i cioX.getMe ssage() +  ".");
  532                                      }
  533                                      catch(Im ageConvers ionInvalid InputExcep tion iciiX )
  534                                      {
  535                                               logger.err or("Input  data error  during co nverting i mage [" +  imageFilen ame + "]",  iciiX);
  536                                               transactio nContext.a ddDebugInf ormation(" ImageConve rsionInval idInputExc eption con verting im age, " + i ciiX.getMe ssage() +  ".");
  537                                      }
  538                                      catch(IO Exception  ioX)
  539                                      {
  540                                               logger.err or("IOExce ption whil e converti ng image [ " + imageF ilename +  "]", ioX);
  541                                               transactio nContext.a ddDebugInf ormation(" IOExceptio n converti ng image,  " + ioX.ge tMessage()  + ".");
  542                                      }
  543                                      
  544                                      if(respo nse.getIma geStream()  != null | | response .getTxtStr eam() != n ull){
  545                                               logger.deb ug("Either  InputStre am or TXTS tream is s till opene d.  Need t o close.") ;
  546                                      }
  547  
  548                                      logger.i nfo("Not a ble to con vert from  [" + store dFormat +  "] to [" +  quality.g etImageFor mat() + "] , trying n ext conver sion optio n");
  549                                      // its n ot necessa ry to clos e the inpu t stream,  if we got  here then  we tried t o do conve rsions
  550                                      // which  means the  image was  buffered  so the buf fering han dled closi ng the inp ut streams
  551                                      logger.i nfo("Re-op ening imag e stream") ;
  552                                      // not r eally sure  if this i s necessar y anymore
  553                                      response  = storage Facade.ope nImageStre am(imageFi lename, 
  554                                                       st orageCrede ntials, St orageProxi mity.OFFLI NE, reques tFormatQua lityList);
  555                                      storedFo rmat = res ponse.getI mageFormat ();
  556                                      storedQu ality = re sponse.get ImageQuali ty();
  557                                      if(store dQuality = = null)
  558                                               storedQual ity = file Path.getIm ageQuality ();
  559                                      if(respo nse.getIma geQuality( ) == null)
  560                                               response.s etImageQua lity(store dQuality);
  561                                      quality  = getNextA llowableIm ageFormatQ uality(sto redFormat,  qualities Iterator);
  562                    
  563                             }
  564                             // if  we got her e then we  couldn't d o anything  to the im age to sat isfy the r equest
  565                             String  msg = "Co uldn't per form accep table [" +  storedFor mat + 
  566                             "] dat a conversi on to matc h requeste d format(s ) [" + con vertFormat QualityLis t.getAccep tString(fa lse) + "]" ;
  567                             //logg er.info(,  throwing I mageConver sionExcept ion");
  568                             logger .error(msg );
  569                             logger .info("Clo sing possi bly still  open image  and TXT s treams");
  570                             if(res ponse.getI mageStream () != null )
  571                                      response .getImageS tream().cl oseSafely( );
  572                             if(res ponse.getT xtStream()  != null)
  573                                      response .getTxtStr eam().clos eSafely();
  574                             throw  new ImageC onversionE xception(m sg);
  575                    }
  576                    fina lly
  577                    {
  578                             if(res ponse != n ull){
  579                                      if(respo nse.getIma geStream()  != null | | response .getTxtStr eam() != n ull){
  580                                               logger.deb ug("Either  InputStre am or TXTS tream is s till opene d.  Need t o close.") ;
  581                                      }
  582                             }
  583                             //retu rnBuffers( );
  584                    }
  585           }
  586  
  587           /* *
  588            *  This meth od parses  an opened  TXT file s tream for  DICOM Moda lity code.
  589            *  Before re turning th e modality  code the  partially  read strea m is close d.
  590            *  @param tx tstream
  591            *                         A sized  InputStrea m referrin g to TXT s tream and  its length
  592            *  @throws I mageConver sionIOExce ption
  593            * /
  594           pr ivate Stri ng getTXTM odality(By teBufferBa ckedInputS tream txtS tream) {
  595                    Stri ng mty="";
  596                String t extLine =  "";
  597                int byte sRead=0;
  598                    if ( (txtStream  == null)  || (!txtSt ream.isRea dable()))
  599                             return  mty;
  600                    try 
  601                    {
  602                             int fs ize = txtS tream.getS ize();
  603                             if (fs ize > 0) {
  604                                 Bu fferedRead er buffer  = new Buff eredReader (new Input StreamRead er(txtStre am.getInpu tStream()) );
  605                                 do {// parse  for "MODAL ITY=" or " Modality|1 ,1|" and t ake the ne xt 2 bytes
  606                                      do{ // g et next li ne
  607                                               if (bytesR ead >= fsi ze)
  608                                                       re turn mty;
  609                                          text Line = buf fer.readLi ne();
  610                                               if(textLin e == null)  // EOF
  611                                               return mty ;
  612                                               bytesRead  += textLin e.length() ;
  613                                      } while  (textLine. equals("") );
  614                                 }  while( !(( textLine.s tartsWith( "MODALITY" )) || (tex tLine.star tsWith("00 08,0060|Mo dality")))  );
  615                                 if  (textLine .startsWit h("MODALIT Y"))
  616                                      mty=text Line.subst ring(textL ine.indexO f("=")+1);
  617                                 el se
  618                                      mty=text Line.subst ring(textL ine.lastIn dexOf("|") +1);
  619                             }
  620                    } 
  621                    catc h (IOExcep tion ioX)  {
  622                             logger .error("Er ror extrac ting Modal ity code f rom TXT st ream", ioX );
  623                    }
  624                    fina lly 
  625                    {
  626                             txtStr eam.closeS afely();
  627                    }
  628                    retu rn mty;
  629           }
  630           
  631           pr ivate bool ean canCom pressForma t(ImageFor mat imageF ormat)
  632           {
  633                    if(i mageFormat  == null){
  634                             logger .debug("im ageFormat  is null.") ;
  635                             return  false;
  636                    }
  637                    Imag eFormatAll owableConv ersionList  conversio nList = ge tImageConf iguration( ).getForma tConfigura tion(image Format);
  638                    if(c onversionL ist == nul l){
  639                             logger .debug("co nversionLi st is null .");
  640                             return  false;
  641                    }
  642                    retu rn convers ionList.is CanCompres s();
  643           }
  644  
  645           /* *
  646            *  Retrieves  a TXT str eam from t he storage  facade.
  647            *  
  648            *  @param im ageFilenam e
  649            *  @param st orageCrede ntials
  650            *  @param hi sUpdate Ha shmap cont aining nam e/value pa irs of the  HIS updat e of patie nt data.
  651            *  @return
  652            * /
  653           pu blic ByteB ufferBacke dInputStre am GetTxtS tream(Stri ng imageFi lename, St orageCrede ntials sto rageCreden tials, 
  654                             HashMa p<String,  String> hi sUpdate)
  655           th rows Image NotFoundEx ception, I mageNearLi neExceptio n, Connect ionExcepti on, Method Exception
  656           {
  657                    logg er.info("O pening str eam to TXT  file for  image [" +  imageFile name + "]" );
  658                    Byte BufferBack edInputStr eam txtStr eam = stor ageFacade. openTXTStr eam(imageF ilename, 
  659                                      storageC redentials , null);
  660                    logg er.info("G ot stream  to TXT fil e for imag e [" + ima geFilename  + "]");
  661                    retu rn appendT xtStreamWi thHisUpdat e(txtStrea m, hisUpda te);
  662           }
  663           
  664           pr ivate Byte BufferBack edInputStr eam getTxt StreamHand leExceptio n(String i mageFilena me, 
  665                             Storag eCredentia ls storage Credential s, HashMap <String, S tring> his Update)
  666           {
  667                    try
  668                    {
  669                             return  GetTxtStr eam(imageF ilename, s torageCred entials, h isUpdate);
  670                    }
  671                    catc h(ImageNot FoundExcep tion infX)
  672                    {
  673                             logger .error("TX T File for  image ["  + imageFil ename + "]  not found ", infX);
  674                    }
  675                    catc h(ImageNea rLineExcep tion inlX)
  676                    {
  677                             logger .error("TX T File for  image ["  + imageFil ename + "]  nearline  exception" , inlX);
  678                    }
  679                    catc h(Connecti onExceptio n cX)
  680                    {
  681                             logger .error("TX T File for  image ["  + imageFil ename + "]  connectio n exceptio n", cX);
  682                    }
  683                    catc h(MethodEx ception mX )
  684                    {
  685                             logger .error("TX T File for  image ["  + imageFil ename + "]  method ex ception",  mX);
  686                    }
  687                    retu rn null;
  688           }
  689  
  690           pr ivate Byte BufferBack edInputStr eam append TxtStreamW ithHisUpda te(ByteBuf ferBackedI nputStream  txtStream
  691                             HashMa p<String,  String> hi sUpdate)
  692           {                 
  693                    /*
  694                    if(( hisUpdate  == null) | | (hisUpda te.size()  <= 0))
  695                             return  txtStream ;
  696                     */
  697                    int  bytesRead  = 0;
  698  
  699                    Stri ngBuilder  sb = new S tringBuild er();
  700  
  701                    sb.a ppend("$$B EGIN HIS U PDATE");
  702                    sb.a ppend("\n" );
  703  
  704                    Stri ng lastKey  = "";
  705                    int  keyCount =  1;
  706                    if(h isUpdate ! = null)
  707                    {
  708                             Set<Ma p.Entry<St ring, Stri ng>> entri es = hisUp date.entry Set();
  709                             for(En try<String , String>  entry : en tries)
  710                             {
  711                                      String k ey = entry .getKey();
  712                                      if(key.e quals(last Key))
  713                                      {
  714                                               keyCount++ ;
  715                                      }
  716  
  717                                      String l ine = key  + StringUt il.STICK +  StringUti l.STICK +  keyCount +  ",1" + St ringUtil.S TICK + ent ry.getValu e();
  718                                      lastKey  = key;
  719                                      sb.appen d(line + " \n");
  720                             }
  721                    }
  722                    sb.a ppend("$$E ND HIS UPD ATE\n");
  723                    byte sRead = sb .length();
  724                    Inpu tStream hi sStream =  IOUtils.to InputStrea m(sb.toStr ing());
  725  
  726                    Byte BufferBack edInputStr eam sizedS tream = nu ll;
  727                    if(t xtStream = = null)
  728                    {
  729                             logger .info("app endTxtStre amWithHisU pdate, txt  stream is  null, ret urning str eam contai ning only  HIS update ");
  730                             sizedS tream = ne w ByteBuff erBackedIn putStream( hisStream,  bytesRead );
  731                    }
  732                    else
  733                    {
  734                              logger.inf o("Co PYR ning HIS s tream with  TXT strea m");
  735                             InputS tream text InputStrea m = txtStr eam.getInp utStream() ;
  736                             Sequen ceInputStr eam seqStr eam = new  SequenceIn putStream( textInputS tream, his Stream);
  737                             logger .info("HIS  Stream ha s been joi ned with T XT stream" );
  738                             sizedS tream = ne w ByteBuff erBackedIn putStream( seqStream,  bytesRead  + txtStre am.getSize ());                        
  739                    }
  740                    retu rn sizedSt ream;
  741           }
  742  
  743           /* *
  744            *  Open the  TXT file s tream
  745            *  @param tx tFilename  The txt fi le to open
  746            *  @param st orageCrede ntials the  storage c redentials  used to a ccess the  image shar e
  747            *  @return T he input s tream to t he file 
  748            *  @throws I mageNotFou ndExceptio n Occurs i f the file  is not fo und or acc essible
  749            *  @throws I mageNearLi neExceptio n Occurs i f the file  is not ac cessible b ut is on a  nearline  storage de vice
  750            * /
  751           /*
  752           pr ivate Size dInputStre am getTXTS tream(Stri ng txtFile name, Stor ageCredent ials stora geCredenti als)
  753           th rows Image NotFoundEx ception, I mageNearLi neExceptio n
  754           {                 
  755                    retu rn SmbStor ageUtility .openFileS tream(txtF ilename, s torageCred entials, S torageProx imity.OFFL INE);              
  756           }
  757            * /
  758  
  759           /* *
  760            *  Returns t he next al lowable im age format  quality f or the sto red format .  
  761            *  @param st oredFormat  the forma t of the s tored imag e
  762            *  @param qu alitiesIte rator The  iterator o f the qual ities requ ested by t he user
  763            *  @return A n image fo rmat quali ty that wa s requeste d by the c lient and  is allowab le for the  stored im age format .
  764            *  Returns n ull if no  format can  be found  that is al lowed for  the stored  format
  765            * /
  766           pr ivate Imag eFormatQua lity getNe xtAllowabl eImageForm atQuality( ImageForma t storedFo rmat, 
  767                             Iterat or<ImageFo rmatQualit y> qualiti esIterator )
  768           {
  769                    logg er.info("F inding nex t allowabl e conversi on type fo r format [ " + stored Format + " ]");
  770                    Imag eFormatAll owableConv ersionList  formatAll owedList =  getImageC onfigurati on().getFo rmatConfig uration(st oredFormat );
  771                    // i f the list  of allowa ble conver sions is n ull, then  no definit ions for t his format  type
  772                    // r eturning f alse to no t allow th e conversi on, not su re if that  is correc t?
  773                    if(f ormatAllow edList ==  null)
  774                    {
  775                             // JMW  2/21/2011  if the im age format  is not in  the confi guration f ile, then  simply ind icate it c an
  776                             // be  converted  into itsel f so if th e user all ows anythi ng, it can  be return ed
  777                             //logg er.warn("L ist of all owed forma ts to conv ert to is  null, retu rning null ");
  778                             logger .warn("Lis t of allow ed formats  to conver t '" + sto redFormat  + "' is nu ll, not fo und in con figuration  file. Cre ating list  only cont aining thi s format") ;
  779                             format AllowedLis t = new Im ageFormatA llowableCo nversionLi st(storedF ormat, fal se);
  780                             // JMW  6/25/2013  - add thi s format a s an allow ed format  to convert  to (conve rt from se lf to self )
  781                             format AllowedLis t.add(stor edFormat);
  782                             //retu rn null;
  783                    }
  784                    whil e(qualitie sIterator. hasNext())
  785                    {
  786                             ImageF ormatQuali ty quality  = qualiti esIterator .next();
  787  
  788                             if((qu ality.getI mageFormat () == Imag eFormat.OR IGINAL) ||
  789                                               (formatAll owedList.i sFormatCon versionAll owed(quali ty.getImag eFormat()) ))
  790                             {
  791                                      logger.i nfo("Found  allowed a nd request ed format  [" + quali ty.getImag eFormat()  + "]");
  792                                      return q uality;
  793                             }
  794                    }
  795                    logg er.info("C ould not f ind any mo re formats  to conver t [" + sto redFormat  + "] into" );
  796                    retu rn null;
  797           }
  798  
  799           /* *
  800            *  Determine s if the s tored form at is comp ressed and  the targe t format i s not comp ressed.
  801            *  
  802            *  @param st oredFormat
  803            *  @param ta rgetFormat
  804            *  @return T rue if the  stored fo rmat is co mpressed a nd target  format is  not compre ssed, fals e otherwis e
  805            * /
  806           pr ivate bool ean isDeco mpress(Ima geFormat s toredForma t, ImageFo rmat targe tFormat)
  807           {
  808                    if(( storedForm at.isCompr essed()) 
  809                                      && (!tar getFormat. isCompress ed()))
  810                    {
  811                             return  true;
  812                    }
  813                    retu rn false;
  814           }
  815  
  816           pr ivate Byte BufferBack edImageStr eamRespons e decompre ssImage(By teBufferBa ckedImageS treamRespo nse stored Image, 
  817                             ImageF ormatQuali ty quality )
  818           th rows Image Conversion InvalidInp utExceptio n, ImageCo nversionIO Exception,  
  819           Im ageConvers ionDecompr essionExce ption, IOE xception
  820           {
  821                    Imag eFormat st oredFormat  = storedI mage.getIm ageFormat( );
  822                    Imag eFormat ta rgetFormat  = quality .getImageF ormat();
  823                    logg er.info("d ecompress  from [" +  storedForm at + "] to  [" + targ etFormat +  "]");                  
  824                    Imag eQuality i mageQualit y = qualit y.getImage Quality();
  825                    IIma geConversi on convers ion = getI mageConver sion();
  826  
  827                    Byte BufferBack edImageInp utStream o utStream =  
  828                             conver sion.Decom pressImage (storedFor mat, targe tFormat, s toredImage .getImageS tream().to BufferedOb ject());
  829                    retu rn new Byt eBufferBac kedImageSt reamRespon se(outStre am, imageQ uality);
  830           }
  831  
  832           pr ivate Byte BufferBack edImageStr eamRespons e compress Image(Stri ng imageFi lename, 
  833                             ByteBu fferBacked ImageStrea mResponse  storedImag e, ImageFo rmatQualit y quality,  String mo dality)
  834           th rows Image Conversion Decompress ionExcepti on, ImageC onversionI OException
  835           Im ageConvers ionInvalid InputExcep tion, Imag eConversio nCompressi onExceptio n,
  836           IO Exception
  837           {
  838                    Imag eFormat st oredFormat  = storedI mage.getIm ageFormat( );
  839                    Imag eFormat ta rgetFormat  = quality .getImageF ormat();
  840                    logg er.info("c ompress fr om [" + st oredFormat  + "] to [ " + target Format + " ]");
  841                             
  842                    Imag eQuality i mageQualit y = qualit y.getImage Quality();
  843                    IIma geConversi on convers ion = getI mageConver sion();
  844  
  845                    Byte BufferBack edImageInp utStream o utStream =  conversio n.Compress Image(imag eQuality,  storedForm at, 
  846                                      targetFo rmat, stor edImage.ge tImageStre am().toBuf feredObjec t(), modal ity);
  847                    retu rn new Byt eBufferBac kedImageSt reamRespon se(outStre am, imageQ uality);
  848           }
  849  
  850           /* *
  851            *  This upda tes the DI COM header  of an exi sting imag e that was  not conve rted. This  ensures t he header
  852            *  for the i mage is co rrect and  up to date .
  853            *  @param st oredImage
  854            *  @param st oredFormat
  855            *  @param im ageQuality
  856            *  @return
  857            *  @throws I mageConver sionDecomp ressionExc eption
  858            *  @throws I mageConver sionIOExce ption
  859            *  @throws I mageConver sionInvali dInputExce ption
  860            *  @throws I mageConver sionCompre ssionExcep tion
  861            * /
  862           pr ivate Byte BufferBack edImageStr eamRespons e updateDI COMHeader( ByteBuffer BackedImag eStreamRes ponse stor edImage, 
  863                             ImageF ormat stor edFormat,  ImageQuali ty imageQu ality)
  864           th rows Image Conversion Decompress ionExcepti on, ImageC onversionI OException
  865           Im ageConvers ionInvalid InputExcep tion, Imag eConversio nCompressi onExceptio n,
  866           IO Exception
  867           {
  868                    // J MW 4/18/20 111 P104 -  Laurel Br idge 3.3.2 2c fix mak es it poss ible for u s to
  869                    // u pdate the  header in  DICOM JPG  images pro perly - th ey are no  longer exc luded
  870                    
  871                    // J MW 12/23/2 010 p104 -  the image  conversio n code has  trouble u pdating DI COM JPG im age header s
  872                    // a void issue s and just  don't bot her updati ng them
  873                    /*
  874                    if(s toredForma t == Image Format.DIC OMJPEG)
  875                    {
  876                             logger .warn("Ima ge stored  in DICOMJP EG format,  not able  to update  DICOM head er for thi s format,  returning  image as s tored.");
  877                             return  storedIma ge;
  878                    }*/
  879                    
  880                    logg er.info("U pdate head er of stor ed format  [" + store dFormat +  "]");            
  881                    IIma geConversi on convers ion = getI mageConver sion();
  882                    Byte BufferBack edImageInp utStream o utStream =  null;
  883                    if(s toredImage .getTxtStr eam() == n ull){
  884                             outStr eam = conv ersion.Upd ateVAImage (storedFor mat, store dImage.get ImageStrea m().toBuff eredObject (),
  885                                               null);
  886                             
  887                    }
  888                    else {
  889                    outS tream = co nversion.U pdateVAIma ge(storedF ormat, sto redImage.g etImageStr eam().toBu fferedObje ct(), 
  890                                               storedImag e.getTxtSt ream().toB ufferedObj ect());
  891                    }
  892                    
  893                    retu rn new Byt eBufferBac kedImageSt reamRespon se(outStre am, imageQ uality);
  894           }
  895           
  896           /* *
  897            *  This meth od updates  the DICOM  image and  handles a ny excepti ons. This  should alw ays return  the image  although  it might
  898            *  be the or iginal ima ge unchang ed 
  899            *  
  900            *  @param st oredImage
  901            *  @param st oredFormat
  902            *  @param im ageQuality
  903            *  @return
  904            * /
  905           pr ivate Imag eStreamRes ponse upda teDICOMHea derHandleE xceptions( ByteBuffer BackedImag eStreamRes ponse stor edImage,
  906                             ImageF ormat stor edFormat,  ImageQuali ty imageQu ality)
  907           {
  908                    // i f DICOM th en try to  update the  DICOM hea der with t he latest  values
  909                    try
  910                    {
  911                             logger .info("Ima ge is in D ICOM forma t, updatin g DICOM he ader with  TXT file a nd HIS upd ates");
  912                             ImageS treamRespo nse update dResponse  = updateDI COMHeader( storedImag e, storedF ormat, ima geQuality) ;
  913                             if(upd atedRespon se == null )
  914                                      logger.e rror("Resp onse from  updating D ICOM heade r was null , this sho uld NEVER  happen!");
  915                             else
  916                                      return u pdatedResp onse;
  917                             // if  got to her e then the  result wa s null (sh ouldn't ha ppen), 
  918                             // but  the curre nt respons e object s hould stil l contain  the image  and text 
  919                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng
  920                    }
  921                    catc h(IOExcept ion ioX)
  922                    {
  923                             logger .error("IO Exception  updating D ICOM heade r, " + ioX .getMessag e() + ". W ill return  image as  stored.");
  924                             // exc eption occ urred but  the curren t response  object sh ould still  contain t he image a nd text 
  925                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng, we can  just retu rn that
  926                    }
  927                    catc h(ImageCon versionDec ompression Exception  icdX)
  928                    {
  929                             logger .error("Im ageConvers ionDecompr essionExce ption upda ting DICOM  header, "  + icdX.ge tMessage()  + ". Will  return im age as sto red.");
  930                             // exc eption occ urred but  the curren t response  object sh ould still  contain t he image a nd text 
  931                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng, we can  just retu rn that
  932                    }
  933                    catc h(ImageCon versionCom pressionEx ception ic cX)
  934                    {
  935                             logger .error("Im ageConvers ionCompres sionExcept ion updati ng DICOM h eader, " +  iccX.getM essage() +  ". Will r eturn imag e as store d.");
  936                             // exc eption occ urred but  the curren t response  object sh ould still  contain t he image a nd text 
  937                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng, we can  just retu rn that
  938                    }
  939                    catc h(ImageCon versionInv alidInputE xception i ciiX)
  940                    {
  941                             logger .error("Im ageConvers ionInvalid InputExcep tion updat ing DICOM  header, "  + iciiX.ge tMessage()  + ". Will  return im age as sto red.", ici iX);
  942                             // exc eption occ urred but  the curren t response  object sh ould still  contain t he image a nd text 
  943                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng, we can  just retu rn that
  944                    }
  945                    catc h(ImageCon versionIOE xception i cioX)
  946                    {
  947                             logger .error("Im ageConvers ionIOExcep tion updat ing DICOM  header, "  + icioX.ge tMessage()  + ". Will  return im age as sto red.");
  948                             // exc eption occ urred but  the curren t response  object sh ould still  contain t he image a nd text 
  949                             // fil e (since i t was buff ered), so  it shouldn 't have to  do anythi ng, we can  just retu rn that
  950                    }
  951                    retu rn storedI mage;
  952           }
  953           
  954           pr ivate void  setImageS treamRespo nseTextFil eIfNecessa ry(ByteBuf ferBackedI mageStream Response s toredImage ,
  955                             ImageF ormat stor edFormat,  String ima geFilename , StorageC redentials  storageCr edentials,  
  956                             HashMa p<String,  String> hi sUpdate, b oolean txt FileAvaila ble)
  957           {
  958                    if(( storedImag e.getTxtSt ream() ==  null) && ( txtFileAva ilable))
  959                    {
  960                             boolea n getTextF ile = fals e;
  961                             if(Ima geFormat.i sDICOMForm at(storedF ormat))
  962                             {
  963                                      if(updat eDicomHead ers)
  964                                      {
  965                                               getTextFil e = true;
  966                                      }
  967                             }
  968                             else
  969                             {
  970                                      getTextF ile = true ;
  971                             }
  972                             if(get TextFile)
  973                             {
  974                                      ByteBuff erBackedIn putStream  txtStream  = getTxtSt reamHandle Exception( imageFilen ame, 
  975                                                       st orageCrede ntials, hi sUpdate);
  976                                      storedIm age.setTxt Stream(txt Stream);
  977                             }
  978                    }        
  979           }
  980  
  981           /* *
  982            *  This meth od is for  compressin g and conv erting ima ges into D ICOM
  983            *  @param st oredImage
  984            *  @param qu ality
  985            *  @return
  986            *  @throws I mageConver sionDecomp ressionExc eption
  987            *  @throws I mageConver sionIOExce ption
  988            *  @throws I mageConver sionInvali dInputExce ption
  989            *  @throws I mageConver sionCompre ssionExcep tion
  990            *  @throws I OException
  991            * /
  992           pr ivate Imag eStreamRes ponse comp ressAndCon vertImage( ByteBuffer BackedImag eStreamRes ponse stor edImage, 
  993                             ImageF ormatQuali ty quality )
  994           th rows Image Conversion Decompress ionExcepti on, ImageC onversionI OException
  995           Im ageConvers ionInvalid InputExcep tion, Imag eConversio nCompressi onExceptio n,
  996           IO Exception
  997           {                 
  998                    Imag eFormat st oredFormat  = storedI mage.getIm ageFormat( );
  999                    Imag eFormat ta rgetFormat  = quality .getImageF ormat();
  1000                    logg er.info("c ompress an d convert  from [" +  storedForm at + "] to  [" + targ etFormat +  "]");
  1001                    
  1002                    if(s toredForma t == targe tFormat)
  1003                    {
  1004                             // the  stored fo rmat is DI COM
  1005                             if(upd ateDicomHe aders)
  1006                             {
  1007                                      logger.i nfo("Store d format i s the same  as target  format, u pdating DI COM header  and retur ning image .");
  1008                                      // if DI COM then t ry to upda te the DIC OM header  with the l atest valu es
  1009                                      return u pdateDICOM HeaderHand leExceptio ns(storedI mage, stor edFormat,  quality.ge tImageQual ity());
  1010                             }
  1011                             logger .info("Sto red format  is the sa me as targ et format,  returning  input.");
  1012                             return  storedIma ge;
  1013                    }
  1014                    
  1015                    else  if (targe tFormat ==  ImageForm at.ORIGINA L)
  1016                    {
  1017                             logger .info("Tar get format  is ORIGIN AL, return ing input" );
  1018                             return  storedIma ge;
  1019                    }
  1020                    Imag eQuality i mageQualit y = qualit y.getImage Quality();
  1021                    IIma geConversi on convers ion = getI mageConver sion();
  1022                    Byte BufferBack edObject t xtObject =  null;
  1023                    if(s toredImage .getTxtStr eam() != n ull)
  1024                             txtObj ect = stor edImage.ge tTxtStream ().toBuffe redObject( );
  1025                    if(i mageQualit y == Image Quality.TH UMBNAIL)
  1026                    {
  1027                             
  1028                             ByteBu fferBacked ImageInput Stream out Stream = c onversion. ConvertIma ge(storedF ormat, tar getFormat,  
  1029                                               imageQuali ty, stored Image.getI mageStream ().toBuffe redObject( ), txtObje ct);
  1030                             return  new ByteB ufferBacke dImageStre amResponse (outStream , imageQua lity);
  1031                    }
  1032                    else
  1033                    {
  1034                             ImageF ormat conv ertFormat  = targetFo rmat;
  1035                             /*
  1036                              // JM W 9/4/2009  - no long er do this  - VRad ne eds DICOM  without do ing J2K, r equestor s hould know  what they  want!
  1037                             if((ta rgetFormat  == ImageF ormat.DICO M)
  1038                                               || (target Format ==  ImageForma t.DICOMJPE G)
  1039                                               || (target Format ==  ImageForma t.DICOMJPE G2000))
  1040                             {
  1041                                      logger.i nfo("Reque st was for  a DICOM t ype, chang ing to DIC OM JPEG 20 00");
  1042                                      convertF ormat = Im ageFormat. DICOMJPEG2 000;
  1043                             }*/
  1044                             ByteBu fferBacked ImageInput Stream out Stream = c onversion. ConvertIma ge(storedF ormat, con vertFormat
  1045                                               imageQuali ty, stored Image.getI mageStream ().toBuffe redObject( ), txtObje ct);
  1046                             return  new ByteB ufferBacke dImageStre amResponse (outStream , imageQua lity);
  1047                    }
  1048           }
  1049  
  1050           pr ivate bool ean reques tAllowsOri ginalImage Type(Image FormatQual ityList re questForma tQualityLi st)
  1051           {
  1052                    if(r equestForm atQualityL ist == nul l){
  1053                             logger .debug("Im ageFormatQ ualityList  is null." );
  1054                             return  false;
  1055                    }
  1056                    
  1057                    for( ImageForma tQuality q uality : r equestForm atQualityL ist)
  1058                    {
  1059                             if(qua lity.getIm ageFormat( ) == Image Format.ORI GINAL){
  1060                                      logger.d ebug("Foun d matched  ImageForma t in Image FormatQual ityList");
  1061                                      return t rue;
  1062                             }
  1063                    }
  1064                    logg er.debug(" Found no m atch in Im ageFormatQ ualityList ");
  1065                    retu rn false;
  1066           }
  1067  
  1068           pr ivate bool ean isStor edFormatIn Request(Im ageFormatQ ualityList  requestFo rmatQualit yList, 
  1069                             ImageF ormat stor edFormat,  ImageQuali ty storedQ uality)
  1070           {
  1071                    if(r equestForm atQualityL ist == nul l)
  1072                             return  false;
  1073                    for( ImageForma tQuality q uality : r equestForm atQualityL ist)
  1074                    {
  1075                             // JMW  1/26/2009  - change  to this fu nction, us ed to comp are format  and quali ty directl y
  1076                             // now , if forma t is the s ame and st oredQualit y >= quali ty, then r eturn true
  1077                             // qua lity must  be better  than or eq ual to to  be true.                    
  1078                             if(qua lity.getIm ageFormat( ) == store dFormat)
  1079                             {
  1080                                      if(quali ty.getImag eQuality() .getCanoni cal() <= s toredQuali ty.getCano nical())
  1081                                               return tru e;
  1082                             }                
  1083                    }
  1084                    retu rn false;
  1085           }
  1086  
  1087           
  1088           pr ivate bool ean isStor edFormatIn Request(Im ageFormatQ ualityList  requestFo rmatQualit yList, 
  1089                             ImageF ormat stor edFormat)
  1090           {
  1091                    if(r equestForm atQualityL ist == nul l)
  1092                             return  false;
  1093                    for( ImageForma tQuality q uality : r equestForm atQualityL ist)
  1094                    {
  1095                             // JMW  1/26/2009  - change  to this fu nction, us ed to comp are format  and quali ty directl y
  1096                             // now , if forma t is the s ame and st oredQualit y >= quali ty, then r eturn true
  1097                             // qua lity must  be better  than or eq ual to to  be true.                    
  1098                             if(qua lity.getIm ageFormat( ) == store dFormat)
  1099                             {
  1100                                      return t rue;
  1101                             }                
  1102                    }
  1103                    retu rn false;
  1104           }
  1105  
  1106  
  1107           /*
  1108           pr ivate Stor ageProximi ty getStor ageProximi tyFromVist aLocation( String img Location)
  1109           {
  1110                    if(I MAGE_LOCAT ION_MAGNET IC.equals( imgLocatio n))
  1111                    {
  1112                             return  StoragePr oximity.ON LINE;
  1113                    }
  1114           }
  1115            * /
  1116   }