aboutsummaryrefslogtreecommitdiffstats
path: root/app/models/import/netex.rb
blob: 753f9128d6d73cdf85bb57f38f8f68642957b87a (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
require 'net/http'
class Import::Netex < Import::Base
  before_destroy :destroy_non_ready_referential

  after_commit do
    main_resource.update_status_from_importer self.status
    true
  end

  before_save do
    self.referential&.failed! if self.status == 'aborted' || self.status == 'failed'
  end

  validates_presence_of :parent

  def main_resource
    @resource ||= parent.resources.find_or_create_by(name: self.name, resource_type: "referential", reference: self.name)
  end

  def notify_parent
    if super
      main_resource.update_status_from_importer self.status
      next_step
    end
  end

  def next_step
    main_resource.next_step
  end

  def create_message args
    main_resource.messages.create args
  end

  def create_with_referential!
    save unless persisted?

    self.referential =
      Referential.new(
        name: self.name,
        organisation_id: workbench.organisation_id,
        workbench_id: workbench.id,
        metadatas: [referential_metadata]
      )
    self.referential.save

    if self.referential.valid?
      main_resource.update referential: referential
      call_iev_callback
      save!
    else
      Rails.logger.info "Can't create referential for import #{self.id}: #{referential.inspect} #{referential.metadatas.inspect} #{referential.errors.messages}"

      if referential.metadatas.all?{|m| m.line_ids.empty? && m.line_ids.empty?}
        create_message criticity: :error, message_key: "referential_creation_missing_lines", message_attributes: {referential_name: referential.name}
      elsif (overlapped_referential_ids = referential.overlapped_referential_ids).any?
        overlapped = Referential.find overlapped_referential_ids.last
        create_message(
          criticity: :error,
          message_key: "referential_creation_overlapping_existing_referential",
          message_attributes: {
            referential_name: referential.name,
            overlapped_name: overlapped.name,
            overlapped_url:  Rails.application.routes.url_helpers.referential_path(overlapped)
          }
        )
      else
        create_message(
          criticity: :error,
          message_key: "referential_creation",
          message_attributes: {referential_name: referential.name},
          resource_attributes: referential.errors.messages
        )
      end
      self.referential = nil
      aborted!
    end
  end

  private

  def iev_callback_url
    URI("#{Rails.configuration.iev_url}/boiv_iev/referentials/importer/new?id=#{id}")
  end

  def destroy_non_ready_referential
    if referential && !referential.ready
      referential.destroy
    end
  end

  def referential_metadata
    metadata = ReferentialMetadata.new

    if self.file && self.file.path
      netex_file = STIF::NetexFile.new(self.file.path)
      frame = netex_file.frames.first

      if frame
        metadata.periodes = frame.periods

        line_objectids = frame.line_refs.map { |ref| "STIF:CODIFLIGNE:Line:#{ref}" }
        metadata.line_ids = workbench.lines.where(objectid: line_objectids).pluck(:id)
      end
    end

    metadata
  end
end