class Layer < ActiveRecord::Base validates_presence_of :name has_many :layers_maps, :dependent => :destroy has_many :maps,:through => :layers_maps belongs_to :user # attr_accessible :bounds after_create :update_layer after_destroy :delete_tileindex def tileindex_filename; self.id.to_s + '.shp' ; end def tileindex_dir defined?(TILEINDEX_DIR) ? TILEINDEX_DIR : File.join(RAILS_ROOT, '/db/maptileindex') end def tileindex_path; File.join(tileindex_dir, tileindex_filename) ; end def mapfile ; self.class.mapfile_path(self.id) ; end def self.mapfile_path(layerid) ; File.join(RAILS_ROOT,"/db/mapfiles/layers/", layerid.to_s + ".map") ; end def thumb if self.maps.first.nil? '/images/missing.png' elsif !self.maps.first.public? '/images/private.png' else self.maps.first.upload.url(:thumb) end end def update_layer create_tileindex save_mapfile get_bounds end # gdaltindex [-tileindex field_name] [-write_absolute_path] [-skip_different_projection] index_file [gdal_file]* def create_tileindex(custom_path=nil) logger.info("create tileindex") tileindex = custom_path || tileindex_path unless self.maps.warped.empty? delete_tileindex(tileindex) map_list = "" #only make a tileindex if the maps are warped. self.maps.warped.each {|map| map_list += (map.warped_filename + " ")} command = "#{GDAL_PATH}gdaltindex -write_absolute_path #{tileindex} #{map_list}" logger.info(command) stdin, stdout, stderr = Open3::popen3(command) out = stdout.readlines.to_s err = stderr.readlines.to_s if !err.match("ERROR 4: Unable to open #{tileindex}").nil? || err.size <= 0 #error saying "Unable to open spec/fixtures/maps/deleteme.shp" is actually okay!! result= true else logger.error("ERROR with gdaltindex "+ err) result= false end else result= false end result end #mapscript getExtent def get_bounds(custom_path=nil) logger.info "get_Bounds" tileindex = custom_path || tileindex_path unless self.maps.warped.empty? command = "#{GDAL_PATH}ogrinfo #{tileindex} -al -so -ro" logger.info command stdin, stdout, stderr = Open3::popen3(command) sout = stdout.readlines.to_s serr = stderr.readlines.to_s if serr.size > 0 logger.debug "Error set bounds with layer get extent "+ serr else extent = sout.scan(/^\w+: \(([0-9\-.]+), ([0-9\-.]+)\) \- \(([0-9\-.]+), ([0-9\-.]+)\)$/).flatten.join(",") update_attribute(:bbox, extent) #self.bbox = extent @bounds = extent #save! end else extent = nil end extent end def save_mapfile(custom_mapfile_path=nil, custom_tileindex=nil) logger.info("save mapfile") layer_name = self.id.to_s wms_name = ERB::Util.html_escape self.name wms_name.gsub!(/\W+/, ' ') layer_map_path = custom_mapfile_path || self.mapfile tileindex = custom_tileindex || self.tileindex_path layermapfile = File.open(layer_map_path, File::CREAT|File::TRUNC|File::RDWR, 0666) template = File.open(RAILS_ROOT+"/db/maptemplates/mapfile_layer.text.erb").read layermapfile.puts ERB.new(template).result( binding ) layermapfile.close return true end def self.save_latest_layers_to_mapfile #save last 50 layers into a mapfile end private def delete_tileindex(custom_path=nil) tileindex = custom_path || tileindex_path if File.exists?(tileindex) basename = File.basename(tileindex, ".shp") basedir = File.dirname(tileindex) logger.info "deleting tileindex" File.delete(tileindex) #shp File.delete( File.join(basedir, (basename+ ".dbf") ) ) File.delete( File.join(basedir, (basename+".shx") ) ) result= true else result= false end result end end