示例#1
0
    def test_read_and_write_of_rasters(self):        
        """Test that rasters can be read and written correctly
        """    
        
        for coveragename in ['Earthquake_Ground_Shaking_clip.tif',
                             'Population_2010_clip.tif',
                             'shakemap_padang_20090930.asc',
                             'population_padang_1.asc']:
        
            filename = 'data/%s' % coveragename
            for R1 in [Raster(filename), read_coverage(filename)]:
                
                # Check consistency of raster
                A1 = R1.get_data()
                M, N = A1.shape
                
                msg = 'Dimensions of raster array do not match those of raster file %s' % R1.filename
                assert M == R1.rows, msg
                assert N == R1.columns, msg        

                # Write back to new file
                outfilename = '/tmp/%s' % coveragename
                try:
                    os.remove(outfilename)
                except:    
                    pass
                
                write_coverage_to_geotiff(A1, outfilename, R1.get_projection(), R1.get_geotransform())
                
                # Read again and check consistency
                R2 = Raster(outfilename)                
                
                msg = 'Dimensions of written raster array do not match those of input raster file\n'
                msg += '    Dimensions of input file %s:  (%s, %s)\n' % (R1.filename, R1.rows, R1.columns)
                msg += '    Dimensions of output file %s: (%s, %s)' % (R2.filename, R2.rows, R2.columns)                
                assert R1.rows == R2.rows, msg
                assert R1.columns == R2.columns, msg                        
        
                A2 = R2.get_data()     
                
                assert numpy.allclose(numpy.min(A1), numpy.min(A2))
                assert numpy.allclose(numpy.max(A1), numpy.max(A2))                

                msg = 'Array values of written raster array were not as expected'
                assert numpy.allclose(A1, A2), msg           
                
                # NOTE: This does not always hold as projection text might differ slightly. E.g.
                #assert R1.get_projection() == R2.get_projection(), msg  
                #E.g. These two refer to the same projection
                #GEOGCS["GCS_WGS_1984",DATUM["WGS_1984",SPHEROID["WGS_1984",6378137.0,298.257223563]],PRIMEM["Greenwich",0.0],UNIT["Degree",0.0174532925199433]]
                #GEOGCS["WGS 84",DATUM["WGS_1984",SPHEROID["WGS 84",6378137,298.2572235630016,AUTHORITY["EPSG","7030"]],AUTHORITY["EPSG","6326"]],PRIMEM["Greenwich",0],UNIT["degree",0.0174532925199433],AUTHORITY["EPSG","4326"]]
                
                msg = 'Geotransforms were different'
                assert R1.get_geotransform() == R2.get_geotransform(), msg                  
示例#2
0
    def calculate(self, hazards, exposures, impact_function_id, impact, bounding_box, comment):
        """Calculate the Impact Geo as a function of Hazards and Exposures
        
        Arguments
            impact_function_id=Id of the impact function to be run 
                               (fully qualified path (from base path))
            hazards = A list of hazard levels .. [H1,H2..HN] each H is a geoserver layer path 
                      where each layer follows the format 
                      username:userpass@geoserver_url:layer_name 
                      (Look at REST for inspiration)
            exposure = A list of exposure levels ..[E1,E2...EN] each E is a 
                       geoserver layer path
            impact = Handle to output impact level layer
            bounding_box = ...
            comment = String with comment for output metadata
        
        Returns
            string: 'SUCCESS' if complete, otherwise Exception is raised

                     
        Note
            hazards and exposure may be lists of handles or just a single handle each.             
        """
        
        # Make sure hazards and exposures are lists
        if type(hazards) != type([]):
            hazards = [hazards]
            
        if type(exposures) != type([]):
            exposures = [exposures]            
        
        # Download data - FIXME(Ole): Currently only raster. FIXME (Ole): Not even sure they should be lists
        
        projection = None
        geotransform = None
        hazard_layers = []
        for hazard in hazards:
            raster = self.get_raster_data(hazard, bounding_box)
            H = raster.get_data()
            hazard_layers.append(H)
            
            # FIXME (Ole): These two could be combined into one thing.
            if projection is None:
                projection = raster.get_projection()
            else:
                msg = 'Projections in hazard levels are different: %s %s' % (projection, raster.get_projection())
                assert projection == raster.get_projection(), msg
                
            if geotransform is None:
                geotransform = raster.get_geotransform()                
            else:
                msg = 'Geotransforms in hazard levels are different: %s %s' % (geotransform, raster.get_geotransform())            
                geotransform == raster.get_geotransform(), msg                
                
                
        exposure_layers = []
        for exposure in exposures:
            raster = self.get_raster_data(exposure, bounding_box)
            E = raster.get_data()
            exposure_layers.append(E)
            
            msg = 'Projections in exposure levels are different: %s %s' % (projection, raster.get_projection())
            assert projection == raster.get_projection(), msg
                
            msg = 'Geotransforms in exposure levels are different: %s %s' % (geotransform, raster.get_geotransform())            
            geotransform == raster.get_geotransform(), msg
            
                        
        # Pass hazard and exposure arrays on to plugin    
        # FIXME, for the time being we just calculate the fatality function assuming only one of each layer.
        
        H = hazard_layers[0]
        E = exposure_layers[0]

        # Calculate impact
        # FIXME (Ole): This is where an impact plugin should be called
        a = 0.97429
        b = 11.037
        F = 10**(a*H-b)*E    
        
        # Upload result
        username, userpass, geoserver_url, layer_name, workspace = self.split_geoserver_layer_handle(impact)
        
        output_file = 'data/%s.tif' % layer_name
        write_coverage_to_geotiff(F, output_file, 
                                  projection=projection,
                                  geotransform=geotransform)
        
        #(FIXME(Ole): still super hacky and not at all general)        
        # FIXME(Ole): Get everything from gdalinfo
        #output_file = 'data/%s.asc' % layer_name
        #write_coverage_to_ascii(F, output_file, 
        #                        xllcorner = bounding_box[0],
        #                        yllcorner = bounding_box[1],
        #                        cellsize=0.030741064,
        #                        #cellsize=0.008333333333000,                                
        #                        nodata_value=-9999,
        #                        # FIXME(Ole): Need to get projection for haz and exp from GeoServer. For now use example.
        #                        projection=open('data/test_grid.prj').read()) 
                                                
        # And upload it again
        lh = self.create_geoserver_layer_handle(username, 
                                                userpass, 
                                                geoserver_url, 
                                                '',
                                                workspace)

        self.upload_geoserver_layer(output_file, lh)
        
        
        return 'SUCCES'