Class: ODDB::BsvXmlPlugin

Inherits:
Plugin show all
Defined in:
src/plugin/bsv_xml.rb,
test/test_plugin/bsv_xml.rb

Defined Under Namespace

Classes: GenericsListener, ItCodesListener, Listener, PreparationsListener

Constant Summary

RECIPIENTS =
[ 'sibylle.imfeld@seconag.com', 'paul.wiederkehr@pharmasuisse.org' ]
BSV_RECIPIENTS =
[ 'jean-christian.krayenbuehl@bag.admin.ch',
'gertrud.fonatsch@bsv.admin.ch', 'hmg@hmg.ch', 'sl-errors-schweiz@googlegroups.com' ]

Constants inherited from Plugin

ARCHIVE_PATH, RECIPIENTS

Instance Attribute Summary (collapse)

Instance Method Summary (collapse)

Methods inherited from Plugin

#l10n_sessions, #recipients, #resolve_link, #update_rss_feeds

Methods included from HttpFile

#http_body, #http_file

Constructor Details

- (BsvXmlPlugin) initialize(*args)

A new instance of BsvXmlPlugin



631
632
633
634
# File 'src/plugin/bsv_xml.rb', line 631

def initialize *args
  @latest = File.join ARCHIVE_PATH, 'xml', 'XMLPublications-latest.zip'
  super
end

Instance Attribute Details

- (Object) preparations_listener (readonly)

Returns the value of attribute preparations_listener



630
631
632
# File 'src/plugin/bsv_xml.rb', line 630

def preparations_listener
  @preparations_listener
end

Instance Method Details

- (Object) _update(path = @latest)



654
655
656
657
658
659
660
661
662
663
664
# File 'src/plugin/bsv_xml.rb', line 654

def _update path=@latest
  Zip::ZipFile.foreach(path) do |entry|
    case entry.name
    when /(\w+)(-\d+)?.xml$/u
      updater = $~[1].gsub(/[A-Z]/u) do |match| "_" << match.downcase end
      entry.get_input_stream do |io| send('update' << updater, io) end
    when 'Publications.xls'
      # do nothing, is not even an xls as of 11.11.2008
    end
  end
end

- (Object) download_file(target_url, save_dir, file_name)



665
666
667
668
669
670
671
672
673
674
675
676
677
678
679
680
681
682
683
684
685
686
687
688
689
690
691
692
693
694
695
696
697
698
699
700
701
702
703
704
705
706
707
708
709
# File 'src/plugin/bsv_xml.rb', line 665

def download_file(target_url, save_dir, file_name)
  LogFile.append('oddb/debug', " getin download_file", Time.now)

  FileUtils.mkdir_p save_dir   # if there is it already, do nothing

  target_file = Mechanize.new.get(target_url)
  save_file = File.join save_dir,
           Date.today.strftime(file_name.gsub(/\./,"-%Y.%m.%d."))
  latest_file = File.join save_dir,
           Date.today.strftime(file_name.gsub(/\./,"-latest."))

  LogFile.append('oddb/debug', " save_file   = " + save_file.to_s, Time.now)
  LogFile.append('oddb/debug', " latest_file = " + latest_file.to_s, Time.now)

  # download target_file temporarily
  temp = Tempfile.new('foo')
  temp_file = temp.path
  target_file.save_as temp_file

  LogFile.append('oddb/debug', " File.exists?(#{latest_file}) = " + File.exists?(latest_file).inspect.to_s, Time.now)
  if(File.exists?(latest_file))
    LogFile.append('oddb/debug', " FileUtils.compare_file(#{temp_file}, #{latest_file}) = " + FileUtils.compare_file(temp_file, latest_file).inspect.to_s, Time.now)
  end

  # check and compare the latest file and save
  if(File.exists?(latest_file) && FileUtils.compare_file(temp_file, latest_file))
    return nil
  else
    target_file.save_as save_file
    FileUtils.cp(save_file, latest_file)
    return save_file
  end
rescue EOFError
  retries ||= 10
  if retries > 0
    retries -= 1
    sleep 10 - retries
    retry
  else
    raise
  end
ensure
  temp.close
  temp.unlink
end

- (Object) log_info



710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753
754
755
756
757
758
759
760
761
762
763
764
765
766
767
768
769
770
771
772
773
774
775
776
777
778
779
780
781
782
783
784
# File 'src/plugin/bsv_xml.rb', line 710

def log_info
  body = report << "\n\n"
  info = super
  parts = [
    [ :duplicate_iksnrs,
      'Duplicate Registrations in SL %d.%m.%Y',
      "Zwei oder mehr \"Preparations\" haben den selben 5-stelligen Swissmedic-Code\n"
    ],
    [ :completed_registrations,
      'Package-Data was completed from SL',
      "die Packungsinformation wurde aus den BAG-XML Daten \303\274bernommen weil von Seiten\nder Swissmedic zur Zeit keine Packungsinformationen zur Verf\303\274gung stehen.\nLimitation (falls vorhanden) und weitere Packungs-Infos wurden ebenfalls\n\303\274bernommen.\n"
    ],
    [ :conflicted_registrations,
      'SMeX/SL-Differences (Registrations) %d.%m.%Y',
      'SL hat anderen 5-Stelligen Swissmedic-Code als SMeX' ],
    [ :conflicted_packages,
      'SMeX/SL-Differences (Packages) %d.%m.%Y',
      'SL hat anderen 8-Stelligen Swissmedic-Code als SMeX' ],
    [ :conflicted_packages_oot,
      'Critical Pharmacodes BAG-XML %d.%m.%Y',
      'SL hat anderen Pharmacode als MedWin' ],
    [ :missing_ikscodes,
      'Missing Swissmedic-Codes in SL %d.%m.%Y',
      'SL hat keinen 8-Stelligen Swissmedic-Code' ],
    [ :missing_pharmacodes,
      'Missing Pharmacodes in SL %d.%m.%Y',
      'SL hat keinen Pharmacode' ],
    [ :missing_ikscodes_oot,
      'Missing Swissmedic-Codes in SL (out of trade) %d.%m.%Y',
      "SL hat keinen 8-Stelligen Swissmedic-Code,\nProdukt ist laut RefData ausser Handel\n"
    ],
    [ :unknown_packages,
      'Unknown Packages in SL %d.%m.%Y',
      "es gibt im SMeX keine Zeile mit diesem 8-stelligen Swissmedic-Code, und\nwir konnten auch keine Automatisierte Zuweisung vornehmen, wir wissen\naber anhand des Pharmacodes, dass die Packung in MedWin vorkommt.\n"
    ],
    [ :unknown_registrations,
      'Unknown Registrations in SL %d.%m.%Y',
      'es gibt im SMeX keine Zeile mit diesem 5-stelligen Swissmedic-Code' ],
    [ :unknown_packages_oot,
      'Unknown Packages in SL (out of trade) %d.%m.%Y',
      "es gibt im SMeX keine Zeile mit diesem 8-stelligen Swissmedic-Code, und\nin MedWin kein Resultat mit dem entsprechenden Pharmacode\n"
    ],
  ].collect do |collection, fmt, explain|
    values = @preparations_listener.send(collection).collect do |data|
      report_format data
    end.sort
    if collection == :conflicted_packages && values.empty?
      next
    end
    name = @@today.strftime fmt
    header = report_format_header(name, values.size)
    body << header << "\n"
    report = [
      header,
      explain,
      values.join("\n\n"),
    ].join("\n")
    ['text/plain', name.gsub(/[\s()\/-]/u, '_') << '.txt', report]
  end
  parts.compact!
  ## combine the last two attachments
  _, _, unknown_pacs = parts.pop
  _, _, unknown_regs = parts.pop
  unknown = unknown_regs << "\n\n" << unknown_pacs
  name = @@today.strftime('Unknown_Products_in_SL_%d.%m.%Y.txt')
  parts.push ['text/plain', name, unknown]
  ## Add some general statistics to the body
  packages = @app.packages
  pcdless = packages.select do |pac| pac.pharmacode.to_s.empty? end
  oots, its = pcdless.partition do |pac| pac.out_of_trade end
  exps, rest = its.partition do |pac| pac.expired? end
  body << "Packungen in der ODDB Total: \#{packages.size}\nPackungen ohne Pharmacode: \#{pcdless.size}\n- ausser Handel: \#{oots.size}\n- inaktive Registration: \#{exps.size}\n- noch nicht auf MedWin: \#{rest.size}\n"
  info.update(:parts => parts, :report => body)
  info
end

- (Object) log_info_bsv



814
815
816
817
818
819
820
821
822
823
824
825
826
827
828
829
830
831
832
833
834
835
836
837
838
839
840
841
842
843
844
845
846
847
848
849
850
851
852
853
854
855
856
857
858
859
860
861
862
863
# File 'src/plugin/bsv_xml.rb', line 814

def log_info_bsv
  body = report_bsv << "\n\n"
  info = { :recipients => recipients.concat(BSV_RECIPIENTS),
           :mail_from => SMTP_FROM }
  parts = [
    [ :conflicted_registrations,
      'SMeX/SL-Differences (Registrations) %d.%m.%Y',
      'SL hat anderen 5-Stelligen Swissmedic-Code als SMeX' ],
    [ :missing_ikscodes,
      'Missing Swissmedic-Codes in SL %d.%m.%Y',
       'SL hat keinen 8-Stelligen Swissmedic-Code' ],
    [ :missing_ikscodes_oot,
      'Missing Swissmedic-Codes in SL (out of trade) %d.%m.%Y',
      "SL hat keinen 8-Stelligen Swissmedic-Code,\nProdukt ist laut RefData ausser Handel\n"
    ],
    [ :unknown_packages,
      'Unknown Packages in SL %d.%m.%Y',
      "es gibt im SMeX keine Zeile mit diesem 8-stelligen Swissmedic-Code, und\nwir konnten auch keine Automatisierte Zuweisung vornehmen, wir wissen\naber anhand des Pharmacodes, dass die Packung in MedWin vorkommt.\n"
    ],
    [ :unknown_registrations,
      'Unknown Registrations in SL %d.%m.%Y',
      'es gibt im SMeX keine Zeile mit diesem 5-stelligen Swissmedic-Code' ],
    [ :unknown_packages_oot,
      'Unknown Packages in SL (out of trade) %d.%m.%Y',
      "es gibt im SMeX keine Zeile mit diesem 8-stelligen Swissmedic-Code, und\nin MedWin kein Resultat mit dem entsprechenden Pharmacode\n"
    ],
    [ :missing_pharmacodes,
      'Missing Pharmacodes in SL %d.%m.%Y',
      'SL hat keinen Pharmacode' ],
    [ :duplicate_iksnrs,
      'Duplicate Registrations in SL %d.%m.%Y',
      "Zwei oder mehr \"Preparations\" haben den selben 5-stelligen Swissmedic-Code\n"
    ],
  ].collect do |collection, fmt, explain|
    values = @preparations_listener.send(collection).collect do |data|
      report_format data
    end.sort
    name = @@today.strftime fmt
    header = report_format_header(name, values.size)
    body << header << "\n"
    report = [
      header,
      explain,
      values.join("\n\n"),
    ].join("\n")
    ['text/plain', name.gsub(/[\s()\/-]/u, '_') << '.txt', report]
  end
  info.update(:parts => parts, :report => body)
  info
end

- (Object) report



880
881
882
883
884
885
886
887
888
# File 'src/plugin/bsv_xml.rb', line 880

def report
  [ 'Created SL-Entries', 'Updated SL-Entries', 'Deleted SL-Entries',
    'Created Limitation-Texts', 'Updated Limitation-Texts',
    'Deleted Limitation-Texts'
  ].collect do |title|
    method = title.downcase.gsub(/[ -]/u, '_')
    report_format_header title, @preparations_listener.send(method)
  end.join("\n")
end

- (Object) report_bsv



889
890
891
892
893
894
895
896
897
# File 'src/plugin/bsv_xml.rb', line 889

def report_bsv
  numbers = [
    :conflicted_registrations, :missing_ikscodes, :missing_ikscodes_oot,
    :unknown_packages, :unknown_registrations, :unknown_packages_oot,
    :missing_pharmacodes, :duplicate_iksnrs ].collect do |key|
    @preparations_listener.send(key).size
  end
  sprintf "Sehr geehrter Herr Krayenb\303\274hl\nSehr geehrte Frau Fonatsch\n\nAm \#{@@today.strftime('%d.%m.%Y')} haben wir Ihren aktuellen SL-Export (XML)\nwieder \303\274berpr\303\274ft. Dabei ist uns folgendes aufgefallen:\n\n1. Bei %i Produkten hat die SL einen anderen 5-Stelligen Swissmedic-Code als\nSwissmedic Excel.\n\n2. Bei %i Produkten hat die SL keinen 8-Stelligen Swissmedic-Code. Ev.\nbefinden sich dort auch Produkte darunter, welche nicht bei der Swissmedic\nregistriert werden m\303\274ssen. Es hat aber sicherlich auch Produkte darunter,\nwelche einen Swissmedic-Code haben sollten.\n\n3. Bei %i Produkten hat die SL keinen 8-Stelligen Swissmedic-Code, die\nProdukte sind laut RefData ausser Handel. Der Swissmedic Code sollte in der SL\ngem\303\244ss SR 830.1, Art. 24, Abs. 1 trotzdem korrekt vorhanden sein. Die\nKrankenkasse muss bis 5 Jahre in der Vergangenheit abrechnen k\303\266nnen.\n\n4. Bei %i Produkten gibt es im Swissmedic-Excel keine Zeile mit diesem\n8-stelligen Swissmedic-Code, die Packung kommt aber in Medwin vor.\n\n5. Bei %i Produkten gibt es im Swissmedic-Excel keine Zeile mit diesem\n5-stelligen Swissmedic-Code. Die Produkte sind aber sicherlich bei der\nSwissmedic registriert.\n\n6. Bei %i Produkten gibt es im Swissmedic-Excel keine Zeile mit diesem\n8-stelligen Swissmedic-Code. Die Produkte sind wohl ausser Handel aber sicher\nnoch bei der Swissmedic registriert. Der Swissmedic Code sollte in der SL\ngem\303\244ss SR 830.1, Art. 24, Abs. 1 trotzdem korrekt vorhanden sein.\n\n7. Bei %i Produkten fehlt der Pharmacode. Hier stellen wir uns die Frage,\nweshalb bei diesen Produkten der Pharmacode fehlt. Eigentlich d\303\274rften keine\nPharmacodes fehlen, denn 99%% Prozent aller Apotheken, Spit\303\244ler, Heime etc.\nrechnen alle mit dem Pharmacode ab.\n\n8. %i 5-stellige Swissmedic-Nummern kommen im BAG-XML-Export doppelt vor.\nSiehe auch Attachment: \#{@@today.strftime('Duplicate_Registrations_in_SL_%d.%m.%Y.txt')}\n\nUm die obigen Beobachtungen kontrollieren zu k\303\266nnen, speichern Sie bitte die\nAttachments auf Ihrem Schreibtisch.\n\nSie k\303\266nnen die Attachments mit dem Windows-Editor \303\266ffnen. Sie finden den\nWindows-Editor unter: Startmenu > Programme > Editor\n\nStarten Sie den Editor und gehen Sie dann auf: Datei > \303\226ffnen\n\nW\303\244hlen sie obige Attachments von Ihrem Schreibtisch aus und schon k\303\266nnen Sie\ndie Attachments anschauen.\n\nDanke f\303\274r Ihr Feedback.\n\nMit freundlichen Gr\303\274ssen\nZeno Davatz\n+41 43 540 05 50\n\n\nAttachments:\n", *numbers
end

- (Object) report_format(hash)



961
962
963
964
965
966
967
968
969
970
971
972
973
974
975
976
977
978
# File 'src/plugin/bsv_xml.rb', line 961

def report_format hash
  [
    :name_base,
    :name_descr,
    :atc_class,
    :generic_type,
    :deductible,
    :pharmacode_bag,
    :pharmacode_oddb,
    :swissmedic_no5_oddb,
    :swissmedic_no8_oddb,
    :swissmedic_no5_bag,
    :swissmedic_no8_bag,
  ].collect do |key|
    label = key.to_s.capitalize.gsub('_', '-') << ':'
    sprintf "%-20s %s", label, hash[key]
  end.join("\n")
end

- (Object) report_format_header(name, size)



958
959
960
# File 'src/plugin/bsv_xml.rb', line 958

def report_format_header name, size
  sprintf "%-58s%5i", name, size
end

- (Object) update



635
636
637
638
639
640
641
642
643
644
645
646
647
648
649
650
651
652
653
# File 'src/plugin/bsv_xml.rb', line 635

def update

  LogFile.append('oddb/debug', " getin BsvXmlPlugin.update", Time.now)

  target_url = ODDB.config.url_bag_sl_zip
  save_dir = File.join ARCHIVE_PATH, 'xml'
  file_name = "XMLPublications.zip"

  LogFile.append('oddb/debug', " target_url = " + target_url.to_s, Time.now)
  LogFile.append('oddb/debug', " save_dir   = " + save_dir.to_s, Time.now)

  path = download_file(target_url, save_dir, file_name)
  LogFile.append('oddb/debug', " path = " + path.inspect.to_s, Time.now)
  #if(path = download_file(target_url, save_dir, file_name))
  if(path)
    _update path
  end
  path
end

- (Object) update_generics(io)



979
980
981
982
# File 'src/plugin/bsv_xml.rb', line 979

def update_generics io
  listener = GenericsListener.new @app
  REXML::Document.parse_stream io, listener
end

- (Object) update_it_codes(io)



983
984
985
986
# File 'src/plugin/bsv_xml.rb', line 983

def update_it_codes io
  listener = ItCodesListener.new @app
  REXML::Document.parse_stream io, listener
end

- (Object) update_preparations(io, opts = {})



987
# File 'src/plugin/bsv_xml.rb', line 987

def update_preparations io, opts={}