diff --git a/docker/debian/Dockerfile b/docker/debian/Dockerfile index 9d7801a3fb9..087905a3f88 100644 --- a/docker/debian/Dockerfile +++ b/docker/debian/Dockerfile @@ -191,7 +191,9 @@ ENV GRASS_SKIP_MAPSET_OWNER_CHECK=1 ENV PROJ_NETWORK=ON # Create generic GRASS lib name regardless of version number -RUN ln -sf /usr/local/grass86 /usr/local/grass +RUN GRASS_DIR="$(find /usr/local -maxdepth 1 -type d -name 'grass*' ! -name 'grass' | sort | tail -n 1)" && \ + test -n "$GRASS_DIR" && \ + ln -sfn "$GRASS_DIR" /usr/local/grass # show GRASS, PROJ, GDAL etc versions RUN grass --tmp-project EPSG:4326 --exec g.version -rge && \ diff --git a/gui/wxpython/lmgr/layertree.py b/gui/wxpython/lmgr/layertree.py index 0b9c042c5c1..0b29db51fa7 100644 --- a/gui/wxpython/lmgr/layertree.py +++ b/gui/wxpython/lmgr/layertree.py @@ -1311,8 +1311,6 @@ def OnPopupGroupOpacityLevel(self, event): if maplayer and ltype != "command": break child = self.GetNextSibling(child) - if child is None: - child, cookie = self.GetNextChild(child, cookie) current_opacity = maplayer.GetOpacity() dlg = SetOpacityDialog( self, diff --git a/lib/cairodriver/draw_bitmap.c b/lib/cairodriver/draw_bitmap.c index d745578817a..058d493b2ac 100644 --- a/lib/cairodriver/draw_bitmap.c +++ b/lib/cairodriver/draw_bitmap.c @@ -12,6 +12,7 @@ */ #include +#include #include "cairodriver.h" @@ -37,7 +38,7 @@ void Cairo_Bitmap(int ncols, int nrows, int threshold, const unsigned char *buf) #define MULTIPLE 4 stride = (ncols + (MULTIPLE - 1)) / MULTIPLE * MULTIPLE; #endif - data = malloc((size_t)stride * nrows); + data = G_malloc((size_t)stride * nrows); surf = cairo_image_surface_create_for_data(data, CAIRO_FORMAT_A8, ncols, nrows, stride); diff --git a/python/grass/temporal/metadata.py b/python/grass/temporal/metadata.py index f892230b00e..6aa3b916073 100644 --- a/python/grass/temporal/metadata.py +++ b/python/grass/temporal/metadata.py @@ -1723,8 +1723,8 @@ def _print_info_body(self, shell: bool = False) -> None: print( " | 3D raster register table:... " + str(self.get_raster3d_register()) ) - print(" | Top-bottom resolution min:.. " + str(self.get_ewres_min())) - print(" | Top-bottom resolution max:.. " + str(self.get_ewres_max())) + print(" | Top-bottom resolution min:.. " + str(self.get_tbres_min())) + print(" | Top-bottom resolution max:.. " + str(self.get_tbres_max())) super()._print_info_body(shell) diff --git a/raster/r.what.color/main.c b/raster/r.what.color/main.c index e314640d732..0b8c5c340b9 100644 --- a/raster/r.what.color/main.c +++ b/raster/r.what.color/main.c @@ -84,13 +84,8 @@ static int do_value(const char *buf, RASTER_MAP_TYPE type, switch (outputFormat) { case PLAIN: fprintf(stdout, "%d: ", ival); - if (strcmp(fmt, "plain") != 0) { - fprintf(stdout, fmt, red, grn, blu); - } - else { - G_color_to_str(red, grn, blu, colorFormat, color_str); - fprintf(stdout, "%s", color_str); - } + G_color_to_str(red, grn, blu, colorFormat, color_str); + fprintf(stdout, "%s", color_str); fprintf(stdout, "\n"); break; diff --git a/scripts/d.correlate/tests/d_correlate_test.py b/scripts/d.correlate/tests/d_correlate_test.py index a7d05b6e4f3..f570ad365d0 100644 --- a/scripts/d.correlate/tests/d_correlate_test.py +++ b/scripts/d.correlate/tests/d_correlate_test.py @@ -33,6 +33,14 @@ def test_fewer_than_two_maps_is_fatal(xy_raster_dataset_session_mapset, tmp_path tools.d_correlate(map="map_a") +def test_exactly_two_maps_runs(xy_raster_dataset_session_mapset, tmp_path): + """d.correlate handles its primary two-map use case without crashing.""" + tools = render_tools(xy_raster_dataset_session_mapset, tmp_path) + tools.r_mapcalc(expression="map_a = col()") + tools.r_mapcalc(expression="map_b = row()") + tools.d_correlate(map="map_a,map_b") + + def test_more_than_two_maps_runs(xy_raster_dataset_session_mapset, tmp_path): """d.correlate handles more than two maps without crashing. diff --git a/scripts/i.oif/i.oif.py b/scripts/i.oif/i.oif.py index d158454bbe0..96dbea55f0a 100755 --- a/scripts/i.oif/i.oif.py +++ b/scripts/i.oif/i.oif.py @@ -142,9 +142,8 @@ def main(): for v, p in oif: sys.stdout.write(fmt % (p + (v,))) else: - outf = open(output, "w") - outf.writelines(fmt % (p + (v,)) for v, p in oif) - outf.close() + with open(output, "w") as outf: + outf.writelines(fmt % (p + (v,)) for v, p in oif) if __name__ == "__main__": diff --git a/scripts/m.proj/m.proj.py b/scripts/m.proj/m.proj.py index 861472f256c..5627c03fa80 100755 --- a/scripts/m.proj/m.proj.py +++ b/scripts/m.proj/m.proj.py @@ -211,9 +211,7 @@ def main(): if coords: x, y = coords.split(",") tmpfile = gcore.tempfile() - fd = open(tmpfile, "w") - fd.write("%s%s%s\n" % (x, ifs, y)) - fd.close() + Path(tmpfile).write_text("%s%s%s\n" % (x, ifs, y)) inf = open(tmpfile) elif input == "-": infile = None diff --git a/scripts/r.in.wms/wms_cap_parsers.py b/scripts/r.in.wms/wms_cap_parsers.py index 5e6d658db11..fe1e5a3d1d9 100644 --- a/scripts/r.in.wms/wms_cap_parsers.py +++ b/scripts/r.in.wms/wms_cap_parsers.py @@ -159,7 +159,7 @@ def _initLayer(self, layer, parent_layer): for element in replaced_elements: elems = layer.findall(self.xml_ns.Ns(element[0])) - if len(elems) != 0 or element[1] == "add": + if len(elems) == 0 or element[1] == "add": for e in parent_layer.findall(self.xml_ns.Ns(element[0])): layer.append(e) diff --git a/scripts/r.in.wms/wms_gdal_drv.py b/scripts/r.in.wms/wms_gdal_drv.py index 2765ccb4ee1..6ec3e3501a9 100644 --- a/scripts/r.in.wms/wms_gdal_drv.py +++ b/scripts/r.in.wms/wms_gdal_drv.py @@ -155,9 +155,8 @@ def _download(self): xml_file = self._createXML() # print xml file content for debug level 1 - file = open(xml_file) - gs.debug("WMS request XML:\n%s" % file.read(), 1) - file.close() + with open(xml_file) as file: + gs.debug("WMS request XML:\n%s" % file.read(), 1) if self.proxy: gdal.SetConfigOption("GDAL_HTTP_PROXY", str(self.proxy)) diff --git a/scripts/v.import/v.import.py b/scripts/v.import/v.import.py index 9a9123e4876..005af9b3c00 100755 --- a/scripts/v.import/v.import.py +++ b/scripts/v.import/v.import.py @@ -251,12 +251,11 @@ def main(): TMPLOC = gs.append_node_pid("tmp_v_import_location") - f = open(SRCGISRC, "w") - f.write("MAPSET: PERMANENT\n") - f.write("GISDBASE: %s\n" % GISDBASE) - f.write("LOCATION_NAME: %s\n" % TMPLOC) - f.write("GUI: text\n") - f.close() + with open(SRCGISRC, "w") as f: + f.write("MAPSET: PERMANENT\n") + f.write("GISDBASE: %s\n" % GISDBASE) + f.write("LOCATION_NAME: %s\n" % TMPLOC) + f.write("GUI: text\n") # create temp location from input without import gs.verbose(_("Creating temporary project for <%s>...") % OGRdatasource) diff --git a/temporal/t.vect.import/tests/t_vect_import_test.py b/temporal/t.vect.import/tests/t_vect_import_test.py index 76f770fe5a5..d9ed2a38c57 100644 --- a/temporal/t.vect.import/tests/t_vect_import_test.py +++ b/temporal/t.vect.import/tests/t_vect_import_test.py @@ -53,6 +53,8 @@ def test_import_formats( ) info = _stvds_tinfo(tools, output) assert info["temporal_type"] == "absolute" + assert info["start_time"] == "2001-01-01 00:00:00" + assert info["end_time"] == "2001-04-01 00:00:00" assert info["number_of_maps"] == 3