From adbdc47c29fed227b492902a623210c868545f1f Mon Sep 17 00:00:00 2001 From: Sheng Zha Date: Wed, 22 Apr 2020 23:53:12 -0700 Subject: [PATCH] [DEV] switch nose with pytest (#18025) * switch nose with pytest * switch centos python to 3.6 * disable dist kvstore tests * skip hanging test --- .github/workflows/os_x_staticbuild.yml | 6 +- 3rdparty/mshadow/mshadow/random.h | 6 +- benchmark/opperf/opperf.py | 0 cd/python/docker/Dockerfile.test | 2 +- cd/python/pypi/pypi_publish.py | 0 cd/utils/artifact_repository.py | 0 ci/dev_menu.py | 6 +- ci/docker/Dockerfile.build.centos7 | 15 +- ci/docker/Dockerfile.build.test.armv7 | 15 +- ci/docker/Dockerfile.build.test.armv8 | 13 +- ci/docker/Dockerfile.build.ubuntu_cpu | 6 - ci/docker/Dockerfile.build.ubuntu_cpu_julia | 6 - ci/docker/Dockerfile.build.ubuntu_cpu_python | 5 +- ci/docker/Dockerfile.build.ubuntu_cpu_scala | 2 +- ci/docker/Dockerfile.build.ubuntu_gpu_cu101 | 6 - ci/docker/Dockerfile.build.ubuntu_nightly_cpu | 6 - ci/docker/Dockerfile.build.ubuntu_nightly_gpu | 6 - ci/docker/install/requirements | 41 +++- ci/docker/install/ubuntu_caffe.sh | 58 ----- ci/docker/install/ubuntu_python.sh | 1 + ci/docker/runtime_functions.sh | 143 +++++------ ci/docker_cache.py | 0 ci/docker_login.py | 0 ci/jenkins/Jenkins_steps.groovy | 67 ++---- ci/jenkins/Jenkinsfile_centos_cpu | 2 +- ci/jenkins/Jenkinsfile_centos_gpu | 2 +- ci/jenkins/Jenkinsfile_clang | 2 +- ci/jenkins/Jenkinsfile_edge | 2 +- ci/jenkins/Jenkinsfile_miscellaneous | 2 +- ci/jenkins/Jenkinsfile_sanity | 2 +- ci/jenkins/Jenkinsfile_tools | 2 +- ci/jenkins/Jenkinsfile_unix_gpu | 8 +- ci/jenkins/Jenkinsfile_website_beta | 2 +- ci/jenkins/Jenkinsfile_website_full | 2 +- ci/jenkins/Jenkinsfile_website_full_pr | 2 +- ci/jenkins/Jenkinsfile_website_mxnet_build | 2 +- ci/jenkins/Jenkinsfile_website_nightly | 2 +- ci/jenkins/Jenkinsfile_windows_cpu | 2 +- ci/jenkins/Jenkinsfile_windows_gpu | 2 +- ci/safe_docker_run.py | 0 ci/test_docker_cache.py | 5 - ci/test_docker_login.py | 4 - ci/test_safe_docker_run.py | 5 - ci/windows/test_py3_cpu.ps1 | 8 +- ci/windows/test_py3_gpu.ps1 | 14 +- conftest.py | 226 ++++++++++++++++++ .../examples/captcha/gen_captcha.py | 0 docker/install/python.sh | 7 +- .../pages/get_started/build_from_source.md | 2 +- example/image-classification/__init__.py | 0 example/image-classification/benchmark.py | 0 .../image-classification/benchmark_score.py | 0 example/image-classification/common/data.py | 0 example/image-classification/common/fit.py | 0 example/image-classification/fine-tune.py | 0 example/image-classification/score.py | 0 .../image-classification/symbols/alexnet.py | 0 .../image-classification/symbols/resnet-v1.py | 0 .../image-classification/symbols/resnetv1.py | 0 example/image-classification/test_score.py | 34 +-- example/image-classification/train_cifar10.py | 0 .../image-classification/train_imagenet.py | 0 example/image-classification/train_mnist.py | 0 example/neural_collaborative_filtering/ci.py | 8 +- .../reinforcement-learning/dqn/dqn_demo.py | 0 .../dqn/dqn_run_test.py | 0 example/ssd/data/demo/download_demo_images.py | 0 example/ssd/dataset/pycocotools/__init__.py | 0 example/ssd/dataset/pycocotools/coco.py | 0 example/ssd/demo.py | 0 example/ssd/tools/prepare_dataset.py | 0 example/ssd/train.py | 0 .../install/ubuntu_onnx.sh => pytest.ini | 26 +- python/README.md | 10 +- python/mxnet/_ffi/base.py | 15 -- python/mxnet/contrib/amp/amp.py | 0 python/mxnet/contrib/amp/loss_scaler.py | 0 python/mxnet/image/detection.py | 4 +- python/mxnet/initializer.py | 0 python/mxnet/module/executor_group.py | 0 python/mxnet/optimizer/optimizer.py | 0 python/mxnet/test_utils.py | 18 -- python/setup.py | 2 +- snapcraft.yaml | 79 ------ tests/README.md | 2 +- tests/jenkins/run_test.sh | 14 +- tests/jenkins/run_test_amzn_linux_gpu.sh | 8 +- tests/jenkins/run_test_ubuntu.sh | 14 +- .../test_broken_links.py | 0 .../compilation_warnings/process_output.py | 0 tests/nightly/dist_device_sync_kvstore.py | 3 +- tests/nightly/estimator/test_estimator_cnn.py | 4 - tests/nightly/estimator/test_sentiment_rnn.py | 4 - .../nightly/test_distributed_training-gpu.sh | 6 +- tests/nightly/test_large_array.py | 21 +- tests/nightly/test_large_vector.py | 7 +- tests/nightly/test_np_random.py | 8 +- tests/nightly/test_optimizer.py | 3 - tests/python/gpu/test_contrib_amp.py | 38 +-- tests/python/gpu/test_deferred_compute_gpu.py | 6 +- tests/python/gpu/test_forward.py | 2 +- tests/python/gpu/test_fusion.py | 3 - tests/python/gpu/test_gluon_contrib_gpu.py | 3 - tests/python/gpu/test_gluon_gpu.py | 9 +- tests/python/gpu/test_gluon_model_zoo_gpu.py | 101 ++++---- tests/python/gpu/test_gluon_transforms.py | 2 +- tests/python/gpu/test_kvstore_gpu.py | 9 +- tests/python/gpu/test_numpy_fallback.py | 5 - tests/python/gpu/test_operator_gpu.py | 14 +- tests/python/gpu/test_predictor.py | 6 +- tests/python/gpu/test_tvm_bridge.py | 4 - tests/python/gpu/test_tvm_op_gpu.py | 27 +++ tests/python/mkl/test_bf16_operator.py | 12 +- tests/python/mkl/test_contrib_amp.py | 14 +- tests/python/mkl/test_mkldnn.py | 3 - tests/python/mkl/test_quantization_mkldnn.py | 4 +- tests/python/mkl/test_subgraph.py | 4 - tests/python/profiling/test_nvtx.py | 4 - .../python/quantization/test_quantization.py | 4 - .../quantization_gpu/test_quantization_gpu.py | 5 - tests/python/tensorrt/lenet5_train.py | 0 tests/python/tensorrt/test_cvnets.py | 5 - tests/python/tensorrt/test_ops.py | 3 - tests/python/tensorrt/test_resnet18.py | 3 - tests/python/tensorrt/test_tensorrt_lenet5.py | 3 - tests/python/train/test_conv.py | 0 tests/python/unittest/common.py | 59 +++-- .../unittest}/onnx/README.md | 0 .../unittest}/onnx/backend.py | 0 .../unittest}/onnx/backend_rep.py | 0 .../unittest}/onnx/backend_test.py | 4 +- .../unittest}/onnx/mxnet_export_test.py | 19 +- .../unittest}/onnx/test_cases.py | 0 .../unittest}/onnx/test_models.py | 128 +++++----- .../unittest}/onnx/test_node.py | 23 +- tests/python/unittest/test_autograd.py | 6 +- tests/python/unittest/test_base.py | 2 - .../python/unittest/test_contrib_autograd.py | 6 +- .../unittest/test_contrib_control_flow.py | 11 +- .../python/unittest/test_contrib_hawkesll.py | 5 - .../python/unittest/test_contrib_operator.py | 4 - .../python/unittest/test_contrib_optimizer.py | 3 - tests/python/unittest/test_contrib_stes_op.py | 3 - .../unittest/test_contrib_svrg_module.py | 4 - .../unittest/test_contrib_svrg_optimizer.py | 4 - tests/python/unittest/test_contrib_text.py | 4 - .../python/unittest/test_deferred_compute.py | 18 +- tests/python/unittest/test_dgl_graph.py | 3 - tests/python/unittest/test_dlpack.py | 3 - tests/python/unittest/test_dynamic_shape.py | 4 - tests/python/unittest/test_engine.py | 6 - tests/python/unittest/test_engine_import.py | 6 +- tests/python/unittest/test_exc_handling.py | 38 ++- tests/python/unittest/test_executor.py | 6 +- tests/python/unittest/test_gluon.py | 79 ++---- .../unittest/test_gluon_batch_processor.py | 10 +- tests/python/unittest/test_gluon_contrib.py | 12 +- tests/python/unittest/test_gluon_data.py | 6 +- .../python/unittest/test_gluon_data_vision.py | 17 +- tests/python/unittest/test_gluon_estimator.py | 24 +- .../unittest/test_gluon_event_handler.py | 16 +- tests/python/unittest/test_gluon_model_zoo.py | 7 +- tests/python/unittest/test_gluon_rnn.py | 4 - tests/python/unittest/test_gluon_trainer.py | 10 +- tests/python/unittest/test_gluon_utils.py | 4 +- .../python/unittest/test_higher_order_grad.py | 30 +-- tests/python/unittest/test_image.py | 99 ++++---- tests/python/unittest/test_infer_shape.py | 7 +- tests/python/unittest/test_infer_type.py | 5 - tests/python/unittest/test_io.py | 23 +- tests/python/unittest/test_kvstore.py | 8 +- tests/python/unittest/test_kvstore_custom.py | 5 +- tests/python/unittest/test_loss.py | 10 +- tests/python/unittest/test_metric.py | 4 - tests/python/unittest/test_metric_perf.py | 4 - tests/python/unittest/test_module.py | 6 +- tests/python/unittest/test_ndarray.py | 16 +- tests/python/unittest/test_numpy_gluon.py | 4 - .../unittest/test_numpy_interoperability.py | 12 +- tests/python/unittest/test_numpy_ndarray.py | 13 +- tests/python/unittest/test_numpy_op.py | 43 ++-- tests/python/unittest/test_operator.py | 41 ++-- tests/python/unittest/test_optimizer.py | 13 +- tests/python/unittest/test_predictor.py | 6 +- tests/python/unittest/test_profiler.py | 8 +- tests/python/unittest/test_random.py | 94 ++++---- tests/python/unittest/test_recordio.py | 2 +- tests/python/unittest/test_rnn.py | 5 +- tests/python/unittest/test_runtime.py | 16 +- tests/python/unittest/test_sparse_ndarray.py | 5 +- tests/python/unittest/test_sparse_operator.py | 5 +- tests/python/unittest/test_subgraph.py | 5 +- tests/python/unittest/test_subgraph_op.py | 19 +- tests/python/unittest/test_symbol.py | 11 +- tests/python/unittest/test_test_utils.py | 7 +- tests/python/unittest/test_thread_local.py | 4 - tests/python/unittest/test_tvm_op.py | 3 - tests/python/unittest/test_viz.py | 3 - tests/requirements.txt | 8 - tools/caffe_converter/test_converter.py | 0 tools/dependencies/README.md | 2 +- tools/diagnose.py | 0 tools/flakiness_checker.py | 20 +- tools/im2rec.py | 0 tools/ipynb2md.py | 0 tools/launch.py | 0 tools/parse_log.py | 0 207 files changed, 1053 insertions(+), 1371 deletions(-) mode change 100755 => 100644 benchmark/opperf/opperf.py mode change 100755 => 100644 cd/python/pypi/pypi_publish.py mode change 100755 => 100644 cd/utils/artifact_repository.py mode change 100755 => 100644 ci/dev_menu.py delete mode 100755 ci/docker/install/ubuntu_caffe.sh mode change 100755 => 100644 ci/docker_cache.py mode change 100755 => 100644 ci/docker_login.py mode change 100755 => 100644 ci/safe_docker_run.py create mode 100644 conftest.py mode change 100755 => 100644 contrib/clojure-package/examples/captcha/gen_captcha.py mode change 100755 => 100644 example/image-classification/__init__.py mode change 100755 => 100644 example/image-classification/benchmark.py mode change 100755 => 100644 example/image-classification/benchmark_score.py mode change 100755 => 100644 example/image-classification/common/data.py mode change 100755 => 100644 example/image-classification/common/fit.py mode change 100755 => 100644 example/image-classification/fine-tune.py mode change 100755 => 100644 example/image-classification/score.py mode change 100755 => 100644 example/image-classification/symbols/alexnet.py mode change 100755 => 100644 example/image-classification/symbols/resnet-v1.py mode change 100755 => 100644 example/image-classification/symbols/resnetv1.py mode change 100755 => 100644 example/image-classification/test_score.py mode change 100755 => 100644 example/image-classification/train_cifar10.py mode change 100755 => 100644 example/image-classification/train_imagenet.py mode change 100755 => 100644 example/image-classification/train_mnist.py mode change 100755 => 100644 example/reinforcement-learning/dqn/dqn_demo.py mode change 100755 => 100644 example/reinforcement-learning/dqn/dqn_run_test.py mode change 100755 => 100644 example/ssd/data/demo/download_demo_images.py mode change 100755 => 100644 example/ssd/dataset/pycocotools/__init__.py mode change 100755 => 100644 example/ssd/dataset/pycocotools/coco.py mode change 100755 => 100644 example/ssd/demo.py mode change 100755 => 100644 example/ssd/tools/prepare_dataset.py mode change 100755 => 100644 example/ssd/train.py rename ci/docker/install/ubuntu_onnx.sh => pytest.ini (55%) mode change 100755 => 100644 mode change 100755 => 100644 python/mxnet/contrib/amp/amp.py mode change 100755 => 100644 python/mxnet/contrib/amp/loss_scaler.py mode change 100755 => 100644 python/mxnet/initializer.py mode change 100755 => 100644 python/mxnet/module/executor_group.py mode change 100755 => 100644 python/mxnet/optimizer/optimizer.py mode change 100755 => 100644 python/mxnet/test_utils.py delete mode 100644 snapcraft.yaml mode change 100755 => 100644 tests/nightly/broken_link_checker_test/test_broken_links.py mode change 100755 => 100644 tests/nightly/compilation_warnings/process_output.py create mode 100644 tests/python/gpu/test_tvm_op_gpu.py mode change 100755 => 100644 tests/python/tensorrt/lenet5_train.py mode change 100644 => 100755 tests/python/train/test_conv.py rename tests/{python-pytest => python/unittest}/onnx/README.md (100%) rename tests/{python-pytest => python/unittest}/onnx/backend.py (100%) rename tests/{python-pytest => python/unittest}/onnx/backend_rep.py (100%) rename tests/{python-pytest => python/unittest}/onnx/backend_test.py (95%) mode change 100755 => 100644 rename tests/{python-pytest => python/unittest}/onnx/mxnet_export_test.py (90%) rename tests/{python-pytest => python/unittest}/onnx/test_cases.py (100%) rename tests/{python-pytest => python/unittest}/onnx/test_models.py (57%) rename tests/{python-pytest => python/unittest}/onnx/test_node.py (94%) mode change 100755 => 100644 tests/python/unittest/test_optimizer.py delete mode 100644 tests/requirements.txt mode change 100755 => 100644 tools/caffe_converter/test_converter.py mode change 100755 => 100644 tools/diagnose.py mode change 100755 => 100644 tools/im2rec.py mode change 100755 => 100644 tools/ipynb2md.py mode change 100755 => 100644 tools/launch.py mode change 100755 => 100644 tools/parse_log.py diff --git a/.github/workflows/os_x_staticbuild.yml b/.github/workflows/os_x_staticbuild.yml index eb7bc0b9b3d9..6727b22c8baf 100644 --- a/.github/workflows/os_x_staticbuild.yml +++ b/.github/workflows/os_x_staticbuild.yml @@ -10,7 +10,8 @@ jobs: uses: actions/checkout@v2 - name: Install Dependencies run: | - brew install nasm automake ninja libtool cmake pkgconfig protobuf + brew install nasm automake ninja libtool cmake pkgconfig protobuf hdf5 zlib + python3 -m pip install --user -r ci/docker/install/requirements - name: Build project run: | git --version @@ -18,8 +19,7 @@ jobs: CMAKE_STATICBUILD=1 ./tools/staticbuild/build.sh cpu - name: Setup Python run: | - python3 -m pip install --user nose nose-timer nose-exclude numpy scipy python3 -m pip install --user -e python - name: Test project run: | - python3 -m nose --with-timer --verbose tests/python/unittest/ --exclude-test=test_extensions.test_subgraph --exclude-test=test_extensions.test_custom_op --exclude-test=test_gluon_data.test_recordimage_dataset_with_data_loader_multiworker --exclude-test=test_gluon_data.test_multi_worker --exclude-test=test_gluon_data.test_multi_worker_shape --exclude-test=test_gluon_data.test_multi_worker_forked_data_loader --exclude-test=test_gluon_data.test_multi_worker_dataloader_release_pool + python3 -m pytest --durations=50 --verbose tests/python/unittest/ -k 'not (test_subgraph or test_custom_op or test_recordimage_dataset_with_data_loader_multiworker or test_multi_worker or test_multi_worker_shape or test_multi_worker_forked_data_loader or test_multi_worker_dataloader_release_pool)' diff --git a/3rdparty/mshadow/mshadow/random.h b/3rdparty/mshadow/mshadow/random.h index 13c34055db1e..95f17ba2b2d5 100644 --- a/3rdparty/mshadow/mshadow/random.h +++ b/3rdparty/mshadow/mshadow/random.h @@ -336,8 +336,10 @@ class Random { * \brief get a set of random integers */ inline void GetRandInt(const Tensor& dst) { - curandStatus_t status = curandGenerate(gen_, dst.dptr_, dst.size(0)); - CHECK_EQ(status, CURAND_STATUS_SUCCESS) << "CURAND Gen rand ints failed."; + curandStatus_t status; + status = curandGenerate(gen_, dst.dptr_, dst.size(0)); + CHECK_EQ(status, CURAND_STATUS_SUCCESS) << "CURAND Gen rand ints failed." + << " size = " << dst.size(0); } /*! * \brief generate data from uniform [a,b) diff --git a/benchmark/opperf/opperf.py b/benchmark/opperf/opperf.py old mode 100755 new mode 100644 diff --git a/cd/python/docker/Dockerfile.test b/cd/python/docker/Dockerfile.test index bed059d0fc73..6ded5f4722fb 100644 --- a/cd/python/docker/Dockerfile.test +++ b/cd/python/docker/Dockerfile.test @@ -24,7 +24,7 @@ ARG BASE_IMAGE FROM ${BASE_IMAGE} # Install test dependencies -RUN pip install nose +RUN pip install pytest ARG USER_ID=1001 ARG GROUP_ID=1001 diff --git a/cd/python/pypi/pypi_publish.py b/cd/python/pypi/pypi_publish.py old mode 100755 new mode 100644 diff --git a/cd/utils/artifact_repository.py b/cd/utils/artifact_repository.py old mode 100755 new mode 100644 diff --git a/ci/dev_menu.py b/ci/dev_menu.py old mode 100755 new mode 100644 index 962e4ecfe03f..365d2b8e9cfc --- a/ci/dev_menu.py +++ b/ci/dev_menu.py @@ -105,8 +105,8 @@ def provision_virtualenv(venv_path=DEFAULT_PYENV): # Install MXNet python bindigs check_call([pip, 'install', '--upgrade', '--force-reinstall', '-e', 'python']) # Install test dependencies - check_call([pip, 'install', '--upgrade', '--force-reinstall', '-r', os.path.join('tests', - 'requirements.txt')]) + check_call([pip, 'install', '--upgrade', '--force-reinstall', '-r', + os.path.join('ci', 'docker', 'install', 'requirements')]) else: logging.warn("Can't find pip: '%s' not found", pip) @@ -119,7 +119,7 @@ def provision_virtualenv(venv_path=DEFAULT_PYENV): provision_virtualenv, ]), ('[Local] Python Unit tests', - "./py3_venv/bin/nosetests -v tests/python/unittest/" + "pytest -v tests/python/unittest/" ), ('[Docker] Build the MXNet binary - outputs to "lib/"', "ci/build.py --platform ubuntu_cpu_lite /work/runtime_functions.sh build_ubuntu_cpu_docs"), diff --git a/ci/docker/Dockerfile.build.centos7 b/ci/docker/Dockerfile.build.centos7 index ce74d9e896b6..2a335848dcb2 100644 --- a/ci/docker/Dockerfile.build.centos7 +++ b/ci/docker/Dockerfile.build.centos7 @@ -51,7 +51,7 @@ RUN yum -y check-update || true && \ protobuf-devel \ # CentOS Software Collections https://www.softwarecollections.org devtoolset-7 \ - rh-python35 \ + rh-python36 \ rh-maven35 \ # Libraries # Provide clbas headerfiles @@ -71,7 +71,7 @@ RUN yum -y check-update || true && \ # Make GCC7, Python 3.5 and Maven 3.3 Software Collections available by default # during build and runtime of this container -SHELL [ "/usr/bin/scl", "enable", "devtoolset-7", "rh-python35", "rh-maven35" ] +SHELL [ "/usr/bin/scl", "enable", "devtoolset-7", "rh-python36", "rh-maven35" ] # Install minimum required cmake version RUN cd /usr/local/src && \ @@ -93,7 +93,16 @@ RUN cd /usr/local/src && \ # Python dependencies RUN pip3 install --no-cache-dir --upgrade pip && \ - pip3 install --no-cache-dir nose pylint cython numpy nose-timer requests h5py scipy==1.2.3 wheel + pip3 install --no-cache-dir pylint cython numpy requests h5py scipy==1.2.3 wheel \ + pytest==5.3.5 \ + pytest-env==0.6.2 \ + pytest-cov==2.8.1 \ + pytest-xdist==1.31.0 \ + pytest-timeout==1.3.4 \ + mock==2.0.0 \ + onnx==1.5.0 \ + protobuf==3.5.2 \ + tabulate==0.7.5 ARG USER_ID=0 diff --git a/ci/docker/Dockerfile.build.test.armv7 b/ci/docker/Dockerfile.build.test.armv7 index d49e7a5582c1..066040c5be8f 100644 --- a/ci/docker/Dockerfile.build.test.armv7 +++ b/ci/docker/Dockerfile.build.test.armv7 @@ -27,15 +27,24 @@ RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y \ python3-pip \ python3-numpy \ python3-scipy \ - python3-nose \ - python3-nose-timer \ python3-requests \ && rm -rf /var/lib/apt/lists/* + +# Python dependencies +RUN pip3 install --no-cache-dir --upgrade pip && \ + pip3 install --no-cache-dir \ + pytest==5.3.5 \ + pytest-env==0.6.2 \ + pytest-cov==2.8.1 \ + pytest-xdist==1.31.0 \ + pytest-timeout==1.3.4 \ + mock==2.0.0 + ARG USER_ID=0 ARG GROUP_ID=0 COPY install/ubuntu_adduser.sh /work/ RUN /work/ubuntu_adduser.sh COPY runtime_functions.sh /work/ -WORKDIR /work/mxnet \ No newline at end of file +WORKDIR /work/mxnet diff --git a/ci/docker/Dockerfile.build.test.armv8 b/ci/docker/Dockerfile.build.test.armv8 index bee4d85c6a97..7a77c78bbeea 100644 --- a/ci/docker/Dockerfile.build.test.armv8 +++ b/ci/docker/Dockerfile.build.test.armv8 @@ -27,15 +27,22 @@ RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y \ python3-pip \ python3-numpy \ python3-scipy \ - python3-nose \ - python3-nose-timer \ python3-requests \ && rm -rf /var/lib/apt/lists/* +RUN pip3 install --no-cache-dir --upgrade pip && \ + pip3 install --no-cache-dir \ + pytest==5.3.5 \ + pytest-env==0.6.2 \ + pytest-cov==2.8.1 \ + pytest-xdist==1.31.0 \ + pytest-timeout==1.3.4 \ + mock==2.0.0 + ARG USER_ID=0 ARG GROUP_ID=0 COPY install/ubuntu_adduser.sh /work/ RUN /work/ubuntu_adduser.sh COPY runtime_functions.sh /work/ -WORKDIR /work/mxnet \ No newline at end of file +WORKDIR /work/mxnet diff --git a/ci/docker/Dockerfile.build.ubuntu_cpu b/ci/docker/Dockerfile.build.ubuntu_cpu index 3c17b748e3ab..86536b206ea3 100644 --- a/ci/docker/Dockerfile.build.ubuntu_cpu +++ b/ci/docker/Dockerfile.build.ubuntu_cpu @@ -54,12 +54,6 @@ RUN /work/ubuntu_gcc8.sh COPY install/ubuntu_mkl.sh /work/ RUN /work/ubuntu_mkl.sh -COPY install/ubuntu_caffe.sh /work/ -RUN /work/ubuntu_caffe.sh - -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_r.sh /work/ COPY install/r.gpg /work/ RUN /work/ubuntu_r.sh diff --git a/ci/docker/Dockerfile.build.ubuntu_cpu_julia b/ci/docker/Dockerfile.build.ubuntu_cpu_julia index 3c17b748e3ab..86536b206ea3 100644 --- a/ci/docker/Dockerfile.build.ubuntu_cpu_julia +++ b/ci/docker/Dockerfile.build.ubuntu_cpu_julia @@ -54,12 +54,6 @@ RUN /work/ubuntu_gcc8.sh COPY install/ubuntu_mkl.sh /work/ RUN /work/ubuntu_mkl.sh -COPY install/ubuntu_caffe.sh /work/ -RUN /work/ubuntu_caffe.sh - -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_r.sh /work/ COPY install/r.gpg /work/ RUN /work/ubuntu_r.sh diff --git a/ci/docker/Dockerfile.build.ubuntu_cpu_python b/ci/docker/Dockerfile.build.ubuntu_cpu_python index 6b217d4d341d..d1b0f6575100 100644 --- a/ci/docker/Dockerfile.build.ubuntu_cpu_python +++ b/ci/docker/Dockerfile.build.ubuntu_cpu_python @@ -32,9 +32,6 @@ COPY install/ubuntu_python.sh /work/ COPY install/requirements /work/ RUN /work/ubuntu_python.sh -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_docs.sh /work/ RUN /work/ubuntu_docs.sh @@ -46,4 +43,4 @@ RUN /work/ubuntu_adduser.sh COPY runtime_functions.sh /work/ -WORKDIR /work/mxnet \ No newline at end of file +WORKDIR /work/mxnet diff --git a/ci/docker/Dockerfile.build.ubuntu_cpu_scala b/ci/docker/Dockerfile.build.ubuntu_cpu_scala index d0ce47784e27..a36e4426c39c 100644 --- a/ci/docker/Dockerfile.build.ubuntu_cpu_scala +++ b/ci/docker/Dockerfile.build.ubuntu_cpu_scala @@ -50,4 +50,4 @@ RUN /work/ubuntu_adduser.sh COPY runtime_functions.sh /work/ -WORKDIR /work/mxnet \ No newline at end of file +WORKDIR /work/mxnet diff --git a/ci/docker/Dockerfile.build.ubuntu_gpu_cu101 b/ci/docker/Dockerfile.build.ubuntu_gpu_cu101 index aa2fdba837e3..a5aa682e5489 100644 --- a/ci/docker/Dockerfile.build.ubuntu_gpu_cu101 +++ b/ci/docker/Dockerfile.build.ubuntu_gpu_cu101 @@ -51,12 +51,6 @@ RUN /work/ubuntu_tvm.sh COPY install/ubuntu_llvm.sh /work/ RUN /work/ubuntu_llvm.sh -COPY install/ubuntu_caffe.sh /work/ -RUN /work/ubuntu_caffe.sh - -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_docs.sh /work/ COPY install/requirements /work/ RUN /work/ubuntu_docs.sh diff --git a/ci/docker/Dockerfile.build.ubuntu_nightly_cpu b/ci/docker/Dockerfile.build.ubuntu_nightly_cpu index 47754b6e2f69..7cf81707b9a7 100644 --- a/ci/docker/Dockerfile.build.ubuntu_nightly_cpu +++ b/ci/docker/Dockerfile.build.ubuntu_nightly_cpu @@ -45,12 +45,6 @@ RUN /work/ubuntu_clang.sh COPY install/ubuntu_gcc8.sh /work/ RUN /work/ubuntu_gcc8.sh -COPY install/ubuntu_caffe.sh /work/ -RUN /work/ubuntu_caffe.sh - -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_r.sh /work/ COPY install/r.gpg /work/ RUN /work/ubuntu_r.sh diff --git a/ci/docker/Dockerfile.build.ubuntu_nightly_gpu b/ci/docker/Dockerfile.build.ubuntu_nightly_gpu index e4e7bd141622..424b9b3aa65c 100644 --- a/ci/docker/Dockerfile.build.ubuntu_nightly_gpu +++ b/ci/docker/Dockerfile.build.ubuntu_nightly_gpu @@ -51,12 +51,6 @@ RUN /work/ubuntu_tvm.sh COPY install/ubuntu_llvm.sh /work/ RUN /work/ubuntu_llvm.sh -COPY install/ubuntu_caffe.sh /work/ -RUN /work/ubuntu_caffe.sh - -COPY install/ubuntu_onnx.sh /work/ -RUN /work/ubuntu_onnx.sh - COPY install/ubuntu_r.sh /work/ COPY install/r.gpg /work/ RUN /work/ubuntu_r.sh diff --git a/ci/docker/install/requirements b/ci/docker/install/requirements index 2d5125e8e2da..94f550b18127 100644 --- a/ci/docker/install/requirements +++ b/ci/docker/install/requirements @@ -18,17 +18,36 @@ # build and install are separated so changes to build don't invalidate # the whole docker cache for the image -boto3==1.9.229 -cpplint==1.3.0 +# Required dependencies +numpy>=1.17 +requests>=2.20.0,<3 +graphviz<0.9.0,>=0.8.1 + +# Optional dependencies +onnx==1.5.0 +# protobuf version frozen due to ps-lite +protobuf==3.5.2 +scipy==1.4.1 +tabulate==0.7.5 Cython==0.29.7 -decorator==4.4.0 -h5py==2.8.0rc1 -mock==2.0.0 -nose==1.3.7 -nose-timer==0.7.3 -numpy>1.16.0,<2.0.0 + +# Development dependencies +cpplint==1.3.0 pylint==2.3.1; python_version >= '3.0' -requests<2.19.0,>=2.18.4 -scipy==1.2.1 -six==1.11.0 +pytest==5.3.5 +pytest-env==0.6.2 +pytest-cov==2.8.1 +pytest-xdist==1.31.0 +pytest-timeout==1.3.4 setuptools +mock==2.0.0 + +# TVM dependencies +decorator==4.4.0 + +# Used in examples +boto3==1.9.229 +h5py==2.10.0 +# TODO(szha): remove once clean-up for py2 is complete +six==1.11.0 +Pillow<6 diff --git a/ci/docker/install/ubuntu_caffe.sh b/ci/docker/install/ubuntu_caffe.sh deleted file mode 100755 index bda1c0b8aef3..000000000000 --- a/ci/docker/install/ubuntu_caffe.sh +++ /dev/null @@ -1,58 +0,0 @@ -#!/usr/bin/env bash - -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, -# software distributed under the License is distributed on an -# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY -# KIND, either express or implied. See the License for the -# specific language governing permissions and limitations -# under the License. -set -ex - -apt-get update || true -apt-get install -y \ - libgflags-dev \ - libgoogle-glog-dev \ - libhdf5-serial-dev \ - libleveldb-dev \ - liblmdb-dev \ - libopencv-dev \ - libprotobuf-dev \ - libsnappy-dev \ - protobuf-compiler \ - python-dev \ - python-numpy \ - python-opencv - -apt-get install -y --no-install-recommends libboost-all-dev - -cd /work/deps -git clone http://github.com/BVLC/caffe.git - -cd caffe -cp Makefile.config.example Makefile.config - -echo "CPU_ONLY := 1" >> Makefile.config - -# Fixes https://github.com/BVLC/caffe/issues/5658 See https://github.com/intel/caffe/wiki/Ubuntu-16.04-or-15.10-Installation-Guide -echo "INCLUDE_DIRS += /usr/lib /usr/lib/x86_64-linux-gnu /usr/include/hdf5/serial/ " >> Makefile.config -echo "LIBRARY_DIRS += /usr/lib /usr/lib/x86_64-linux-gnu /usr/lib/x86_64-linux-gnu/hdf5/serial " >> Makefile.config - -# Fixes https://github.com/BVLC/caffe/issues/4333 See https://github.com/intel/caffe/wiki/Ubuntu-16.04-or-15.10-Installation-Guide -# Note: This is only valid on Ubuntu16.04 - the version numbers are bound to the distribution -ln -s /usr/lib/x86_64-linux-gnu/libhdf5_serial.so.10.0.2 /usr/lib/x86_64-linux-gnu/libhdf5.so -ln -s /usr/lib/x86_64-linux-gnu/libhdf5_serial_hl.so.10.0.2 /usr/lib/x86_64-linux-gnu/libhdf5_hl.so - -make all pycaffe -j$(nproc) - -cd python -for req in $(cat requirements.txt); do pip3 install $req; done diff --git a/ci/docker/install/ubuntu_python.sh b/ci/docker/install/ubuntu_python.sh index b6792a286fad..6234aac12283 100755 --- a/ci/docker/install/ubuntu_python.sh +++ b/ci/docker/install/ubuntu_python.sh @@ -24,6 +24,7 @@ set -ex # install libraries for mxnet's python package on ubuntu apt-get update || true apt-get install -y python-dev python3-dev virtualenv wget +apt-get install -y libprotobuf-dev protobuf-compiler # the version of the pip shipped with ubuntu may be too lower, install a recent version here wget -nv https://bootstrap.pypa.io/get-pip.py diff --git a/ci/docker/runtime_functions.sh b/ci/docker/runtime_functions.sh index b5ca88840384..458b1bc8a45a 100755 --- a/ci/docker/runtime_functions.sh +++ b/ci/docker/runtime_functions.sh @@ -22,8 +22,6 @@ set -ex -NOSE_COVERAGE_ARGUMENTS="--with-coverage --cover-inclusive --cover-xml --cover-branches --cover-package=mxnet" -NOSE_TIMER_ARGUMENTS="--with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error" CI_CUDA_COMPUTE_CAPABILITIES="-gencode=arch=compute_52,code=sm_52 -gencode=arch=compute_70,code=sm_70" CI_CMAKE_CUDA_ARCH="5.2 7.0" @@ -974,16 +972,15 @@ sanity_check() { make cpplint jnilint make -f R-package/Makefile rcpplint make pylint - nosetests-3.4 tests/tutorials/test_sanity_tutorials.py + pytest tests/tutorials/test_sanity_tutorials.py } # Tests libmxnet # Parameters: # $1 -> mxnet_variant: The variant of the libmxnet.so library -# $2 -> python_cmd: The python command to use to execute the tests, python or python3 cd_unittest_ubuntu() { set -ex - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable export PYTHONPATH=./python/ export MXNET_MKLDNN_DEBUG=0 # Ignored if not present export MXNET_STORAGE_FALLBACK_LOG_VERBOSE=0 @@ -994,10 +991,8 @@ cd_unittest_ubuntu() { local mxnet_variant=${1:?"This function requires a mxnet variant as the first argument"} - local nose_cmd="nosetests-3.4" - - $nose_cmd $NOSE_TIMER_ARGUMENTS --verbose tests/python/unittest - $nose_cmd $NOSE_TIMER_ARGUMENTS --verbose tests/python/quantization + pytest --durations=50 --verbose tests/python/unittest + pytest --durations=50 --verbose tests/python/quantization # https://github.com/apache/incubator-mxnet/issues/11801 # if [[ ${mxnet_variant} = "cpu" ]] || [[ ${mxnet_variant} = "mkl" ]]; then @@ -1005,15 +1000,15 @@ cd_unittest_ubuntu() { # fi if [[ ${mxnet_variant} = cu* ]]; then - $nose_cmd $NOSE_TIMER_ARGUMENTS --verbose tests/python/gpu + pytest --durations=50 --verbose tests/python/gpu # Adding these here as CI doesn't test all CUDA environments - python3 example/image-classification/test_score.py + pytest example/image-classification/test_score.py integrationtest_ubuntu_gpu_dist_kvstore fi - if [[ ${mxnet_variant} = cpu ]]; then - $nose_cmd $NOSE_TIMER_ARGUMENTS --verbose tests/python/mkl + if [[ ${mxnet_variant} = *mkl ]]; then + pytest --durations=50 --verbose tests/python/mkl fi } @@ -1025,8 +1020,8 @@ unittest_ubuntu_python3_cpu() { export MXNET_SUBGRAPH_VERBOSE=0 export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_unittest.xml --verbose tests/python/unittest - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_quantization.xml --verbose tests/python/quantization + pytest --durations=50 --cov-report xml:tests_unittest.xml --verbose tests/python/unittest + pytest --durations=50 --cov-report xml:tests_quantization.xml --verbose tests/python/quantization } unittest_ubuntu_python3_cpu_mkldnn() { @@ -1037,8 +1032,8 @@ unittest_ubuntu_python3_cpu_mkldnn() { export MXNET_SUBGRAPH_VERBOSE=0 export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_unittest.xml --verbose tests/python/unittest - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_mkl.xml --verbose tests/python/mkl + pytest --durations=50 --cov-report xml:tests_unittest.xml --verbose tests/python/unittest + pytest --durations=50 --cov-report xml:tests_mkl.xml --verbose tests/python/mkl } unittest_ubuntu_python3_gpu() { @@ -1050,7 +1045,7 @@ unittest_ubuntu_python3_gpu() { export CUDNN_VERSION=${CUDNN_VERSION:-7.0.3} export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_gpu.xml --verbose tests/python/gpu + pytest --durations=50 --cov-report xml:tests_gpu.xml --verbose tests/python/gpu } unittest_ubuntu_python3_gpu_cython() { @@ -1064,7 +1059,7 @@ unittest_ubuntu_python3_gpu_cython() { export MXNET_ENFORCE_CYTHON=1 export DMLC_LOG_STACK_TRACE_DEPTH=10 check_cython - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_gpu.xml --verbose tests/python/gpu + pytest --durations=50 --cov-report xml:tests_gpu.xml --verbose tests/python/gpu } unittest_ubuntu_python3_gpu_nocudnn() { @@ -1075,7 +1070,7 @@ unittest_ubuntu_python3_gpu_nocudnn() { export CUDNN_OFF_TEST_ONLY=true export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_gpu.xml --verbose tests/python/gpu + pytest --durations=50 --cov-report xml:tests_gpu.xml --verbose tests/python/gpu } unittest_ubuntu_tensorrt_gpu() { @@ -1087,8 +1082,8 @@ unittest_ubuntu_tensorrt_gpu() { export CUDNN_VERSION=${CUDNN_VERSION:-7.0.3} export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - tests/python/tensorrt/lenet5_train.py - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_trt_gpu.xml --verbose --nocapture tests/python/tensorrt/ + python3 tests/python/tensorrt/lenet5_train.py + pytest --durations=50 --cov-report xml:tests_trt_gpu.xml --verbose --capture=no tests/python/tensorrt/ } # quantization gpu currently only runs on P3 instances @@ -1096,7 +1091,7 @@ unittest_ubuntu_tensorrt_gpu() { unittest_ubuntu_python3_quantization_gpu() { set -ex if [ -f /etc/redhat-release ]; then - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable fi export PYTHONPATH=./python/ export MXNET_MKLDNN_DEBUG=0 # Ignored if not present @@ -1105,7 +1100,7 @@ unittest_ubuntu_python3_quantization_gpu() { export CUDNN_VERSION=${CUDNN_VERSION:-7.0.3} export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_quantization_gpu.xml --verbose tests/python/quantization_gpu + pytest --durations=50 --cov-report xml:tests_quantization_gpu.xml --verbose tests/python/quantization_gpu } unittest_centos7_cpu_scala() { @@ -1245,29 +1240,29 @@ unittest_ubuntu_cpu_julia10() { unittest_centos7_cpu() { set -ex - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable cd /work/mxnet - python -m "nose" $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_unittest.xml --verbose tests/python/unittest - python -m "nose" $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_train.xml --verbose tests/python/train + python -m pytest --durations=50 --cov-report xml:tests_unittest.xml --verbose tests/python/unittest + python -m pytest --durations=50 --cov-report xml:tests_train.xml --verbose tests/python/train } unittest_centos7_gpu() { set -ex - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable cd /work/mxnet export CUDNN_VERSION=${CUDNN_VERSION:-7.0.3} export DMLC_LOG_STACK_TRACE_DEPTH=10 - python3 -m "nose" $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_gpu.xml --verbose tests/python/gpu + python3 -m pytest --durations=50 --cov-report xml:tests_gpu.xml --verbose tests/python/gpu } integrationtest_ubuntu_cpu_onnx() { set -ex export PYTHONPATH=./python/ export DMLC_LOG_STACK_TRACE_DEPTH=10 - tests/python-pytest/onnx/backend_test.py - pytest tests/python-pytest/onnx/mxnet_export_test.py - pytest tests/python-pytest/onnx/test_models.py - pytest tests/python-pytest/onnx/test_node.py + python3 tests/python/unittest/onnx/backend_test.py + pytest tests/python/unittest/onnx/mxnet_export_test.py + pytest tests/python/unittest/onnx/test_models.py + pytest tests/python/unittest/onnx/test_node.py } integrationtest_ubuntu_gpu_python() { @@ -1276,14 +1271,7 @@ integrationtest_ubuntu_gpu_python() { export MXNET_STORAGE_FALLBACK_LOG_VERBOSE=0 export MXNET_SUBGRAPH_VERBOSE=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - example/image-classification/test_score.py -} - -integrationtest_ubuntu_gpu_caffe() { - set -ex - export PYTHONPATH=/work/deps/caffe/python:./python - export DMLC_LOG_STACK_TRACE_DEPTH=10 - tools/caffe_converter/test_converter.py + pytest example/image-classification/test_score.py } integrationtest_ubuntu_cpu_asan() { @@ -1379,10 +1367,9 @@ test_ubuntu_cpu_python3() { source $VENV/bin/activate cd /work/mxnet/python - pip3 install nose nose-timer pip3 install -e . cd /work/mxnet - python3 -m "nose" $NOSE_COVERAGE_ARGUMENTS $NOSE_TIMER_ARGUMENTS --verbose tests/python/unittest + python3 -m pytest $TEST_TIMER_ARGUMENTS --verbose tests/python/unittest popd } @@ -1396,7 +1383,7 @@ unittest_ubuntu_python3_arm() { export MXNET_SUBGRAPH_VERBOSE=0 export MXNET_ENABLE_CYTHON=0 export DMLC_LOG_STACK_TRACE_DEPTH=10 - python3 -m nose --verbose tests/python/unittest/test_engine.py + python3 -m pytest --verbose tests/python/unittest/test_engine.py } # Functions that run the nightly Tests: @@ -1470,9 +1457,9 @@ nightly_test_large_tensor() { set -ex export PYTHONPATH=./python/ export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 tests/nightly/test_large_array.py:test_tensor - nosetests-3.4 tests/nightly/test_large_array.py:test_nn - nosetests-3.4 tests/nightly/test_large_array.py:test_basic + pytest tests/nightly/test_large_array.py::test_tensor + pytest tests/nightly/test_large_array.py::test_nn + pytest tests/nightly/test_large_array.py::test_basic } #Test Large Vectors @@ -1480,9 +1467,9 @@ nightly_test_large_vector() { set -ex export PYTHONPATH=./python/ export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 tests/nightly/test_large_vector.py:test_tensor - nosetests-3.4 tests/nightly/test_large_vector.py:test_nn - nosetests-3.4 tests/nightly/test_large_vector.py:test_basic + pytest tests/nightly/test_large_vector.py::test_tensor + pytest tests/nightly/test_large_vector.py::test_nn + pytest tests/nightly/test_large_vector.py::test_basic } #Test Large Vectors @@ -1490,9 +1477,9 @@ nightly_test_large_vector() { set -ex export PYTHONPATH=./python/ export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 tests/nightly/test_large_vector.py:test_tensor - nosetests-3.4 tests/nightly/test_large_vector.py:test_nn - nosetests-3.4 tests/nightly/test_large_vector.py:test_basic + pytest tests/nightly/test_large_vector.py::test_tensor + pytest tests/nightly/test_large_vector.py::test_nn + pytest tests/nightly/test_large_vector.py::test_basic } #Tests Amalgamation Build with 5 different sets of flags @@ -1536,26 +1523,6 @@ nightly_model_backwards_compat_train() { ./tests/nightly/model_backwards_compatibility_check/train_mxnet_legacy_models.sh } -nightly_straight_dope_python3_single_gpu_tests() { - set -ex - cd /work/mxnet/tests/nightly/straight_dope - export PYTHONPATH=/work/mxnet/python/ - export MXNET_TEST_KERNEL=python3 - export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_straight_dope_python3_single_gpu.xml \ - test_notebooks_single_gpu.py --nologcapture -} - -nightly_straight_dope_python3_multi_gpu_tests() { - set -ex - cd /work/mxnet/tests/nightly/straight_dope - export PYTHONPATH=/work/mxnet/python/ - export MXNET_TEST_KERNEL=python3 - export DMLC_LOG_STACK_TRACE_DEPTH=10 - nosetests-3.4 $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_straight_dope_python3_multi_gpu.xml \ - test_notebooks_multi_gpu.py --nologcapture -} - nightly_tutorial_test_ubuntu_python3_gpu() { set -ex cd /work/mxnet/docs @@ -1568,7 +1535,7 @@ nightly_tutorial_test_ubuntu_python3_gpu() { export PYTHONPATH=/work/mxnet/python/ export MXNET_TUTORIAL_TEST_KERNEL=python3 cd /work/mxnet/tests/tutorials - nosetests-3.4 $NOSE_TIMER_ARGUMENTS --with-xunit --xunit-file nosetests_tutorials.xml test_tutorials.py --nologcapture + pytest --durations=50 --cov-report xml:tests_tutorials.xml --capture=no test_tutorials.py } nightly_java_demo_test_cpu() { @@ -1592,8 +1559,8 @@ nightly_estimator() { export DMLC_LOG_STACK_TRACE_DEPTH=10 cd /work/mxnet/tests/nightly/estimator export PYTHONPATH=/work/mxnet/python/ - nosetests test_estimator_cnn.py - nosetests test_sentiment_rnn.py + pytest test_estimator_cnn.py + pytest test_sentiment_rnn.py } # For testing PRs @@ -1947,7 +1914,7 @@ build_static_libmxnet() { set -ex pushd . source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable export USE_SYSTEM_CUDA=1 local mxnet_variant=${1:?"This function requires a python command as the first argument"} source tools/staticbuild/build.sh ${mxnet_variant} @@ -1959,7 +1926,7 @@ cd_package_pypi() { set -ex pushd . source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable local mxnet_variant=${1:?"This function requires a python command as the first argument"} ./cd/python/pypi/pypi_package.sh ${mxnet_variant} popd @@ -1968,33 +1935,31 @@ cd_package_pypi() { # Sanity checks wheel file cd_integration_test_pypi() { set -ex - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable local gpu_enabled=${1:-"false"} local test_conv_params='' local mnist_params='' - local pip_cmd='pip3' - if [ "${gpu_enabled}" = "true" ]; then mnist_params="--gpu 0" test_conv_params="--gpu" fi # install mxnet wheel package - ${pip_cmd} install --user ./wheel_build/dist/*.whl + pip3 install --user ./wheel_build/dist/*.whl # execute tests - ${python_cmd} /work/mxnet/tests/python/train/test_conv.py ${test_conv_params} - ${python_cmd} /work/mxnet/example/image-classification/train_mnist.py ${mnist_params} + python3 /work/mxnet/tests/python/train/test_conv.py ${test_conv_params} + python3 /work/mxnet/example/image-classification/train_mnist.py ${mnist_params} } # Publishes wheel to PyPI cd_pypi_publish() { set -ex pip3 install --user twine - ./cd/python/pypi/pypi_publish.py `readlink -f wheel_build/dist/*.whl` + python3 ./cd/python/pypi/pypi_publish.py `readlink -f wheel_build/dist/*.whl` } cd_s3_publish() { @@ -2026,7 +1991,7 @@ build_static_python_cpu() { pushd . export mxnet_variant=cpu source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable ./ci/publish/python/build.sh popd } @@ -2037,7 +2002,7 @@ build_static_python_cu92() { export mxnet_variant=cu92 export USE_SYSTEM_CUDA=1 source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable ./ci/publish/python/build.sh popd } @@ -2048,7 +2013,7 @@ build_static_python_cpu_cmake() { export mxnet_variant=cpu export CMAKE_STATICBUILD=1 source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable ./ci/publish/python/build.sh popd } @@ -2060,7 +2025,7 @@ build_static_python_cu92_cmake() { export CMAKE_STATICBUILD=1 export USE_SYSTEM_CUDA=1 source /opt/rh/devtoolset-7/enable - source /opt/rh/rh-python35/enable + source /opt/rh/rh-python36/enable ./ci/publish/python/build.sh popd } diff --git a/ci/docker_cache.py b/ci/docker_cache.py old mode 100755 new mode 100644 diff --git a/ci/docker_login.py b/ci/docker_login.py old mode 100755 new mode 100644 diff --git a/ci/jenkins/Jenkins_steps.groovy b/ci/jenkins/Jenkins_steps.groovy index bfa517364e35..f69364982b57 100644 --- a/ci/jenkins/Jenkins_steps.groovy +++ b/ci/jenkins/Jenkins_steps.groovy @@ -807,8 +807,8 @@ def test_unix_python3_cpu() { python3_ut('ubuntu_cpu') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_cpu_unittest.xml') - utils.collect_test_results_unix('nosetests_quantization.xml', 'nosetests_python3_cpu_quantization.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_cpu_unittest.xml') + utils.collect_test_results_unix('tests_quantization.xml', 'tests_python3_cpu_quantization.xml') } } } @@ -824,8 +824,8 @@ def test_unix_python3_mkl_cpu() { python3_ut('ubuntu_cpu') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_cpu_unittest.xml') - utils.collect_test_results_unix('nosetests_quantization.xml', 'nosetests_python3_cpu_quantization.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_cpu_unittest.xml') + utils.collect_test_results_unix('tests_quantization.xml', 'tests_python3_cpu_quantization.xml') } } } @@ -841,7 +841,7 @@ def test_unix_python3_gpu() { python3_gpu_ut_cython('ubuntu_gpu_cu101') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_gpu.xml', 'nosetests_python3_gpu.xml') + utils.collect_test_results_unix('tests_gpu.xml', 'tests_python3_gpu.xml') } } } @@ -857,7 +857,7 @@ def test_unix_python3_gpu_no_tvm_op() { python3_gpu_ut_cython('ubuntu_gpu_cu101') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_gpu.xml', 'nosetests_python3_gpu.xml') + utils.collect_test_results_unix('tests_gpu.xml', 'tests_python3_gpu.xml') } } } @@ -874,7 +874,7 @@ def test_unix_python3_quantize_gpu() { utils.docker_run('ubuntu_gpu_cu101', 'unittest_ubuntu_python3_quantization_gpu', true) utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_quantization_gpu.xml', 'nosetests_python3_quantize_gpu.xml') + utils.collect_test_results_unix('tests_quantization_gpu.xml', 'tests_python3_quantize_gpu.xml') } } } @@ -890,8 +890,8 @@ def test_unix_python3_debug_cpu() { utils.unpack_and_init('cpu_debug', mx_cmake_lib_debug, true) python3_ut('ubuntu_cpu') } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_cpu_debug_unittest.xml') - utils.collect_test_results_unix('nosetests_quantization.xml', 'nosetests_python3_cpu_debug_quantization.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_cpu_debug_unittest.xml') + utils.collect_test_results_unix('tests_quantization.xml', 'tests_python3_cpu_debug_quantization.xml') } } } @@ -906,8 +906,8 @@ def test_unix_python3_cpu_no_tvm_op() { utils.unpack_and_init('cpu_openblas_no_tvm_op', mx_cmake_lib_no_tvm_op) python3_ut('ubuntu_cpu') } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_cpu_no_tvm_op_unittest.xml') - utils.collect_test_results_unix('nosetests_quantization.xml', 'nosetests_python3_cpu_no_tvm_op_quantization.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_cpu_no_tvm_op_unittest.xml') + utils.collect_test_results_unix('tests_quantization.xml', 'tests_python3_cpu_no_tvm_op_quantization.xml') } } } @@ -923,8 +923,8 @@ def test_unix_python3_mkldnn_cpu() { python3_ut_mkldnn('ubuntu_cpu') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_mkldnn_cpu_unittest.xml') - utils.collect_test_results_unix('nosetests_mkl.xml', 'nosetests_python3_mkldnn_cpu_mkl.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_mkldnn_cpu_unittest.xml') + utils.collect_test_results_unix('tests_mkl.xml', 'tests_python3_mkldnn_cpu_mkl.xml') } } } @@ -940,8 +940,8 @@ def test_unix_python3_mkldnn_mkl_cpu() { python3_ut_mkldnn('ubuntu_cpu') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_mkldnn_cpu_unittest.xml') - utils.collect_test_results_unix('nosetests_mkl.xml', 'nosetests_python3_mkldnn_cpu_mkl.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_mkldnn_cpu_unittest.xml') + utils.collect_test_results_unix('tests_mkl.xml', 'tests_python3_mkldnn_cpu_mkl.xml') } } } @@ -957,7 +957,7 @@ def test_unix_python3_mkldnn_gpu() { python3_gpu_ut('ubuntu_gpu_cu101') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_gpu.xml', 'nosetests_python3_mkldnn_gpu.xml') + utils.collect_test_results_unix('tests_gpu.xml', 'tests_python3_mkldnn_gpu.xml') } } } @@ -973,7 +973,7 @@ def test_unix_python3_mkldnn_nocudnn_gpu() { python3_gpu_ut_nocudnn('ubuntu_gpu_cu101') utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_gpu.xml', 'nosetests_python3_mkldnn_gpu_nocudnn.xml') + utils.collect_test_results_unix('tests_gpu.xml', 'tests_python3_mkldnn_gpu_nocudnn.xml') } } } @@ -990,7 +990,7 @@ def test_unix_python3_tensorrt_gpu() { utils.docker_run('ubuntu_gpu_tensorrt', 'unittest_ubuntu_tensorrt_gpu', true) utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_tensorrt.xml', 'nosetests_python3_tensorrt_gpu.xml') + utils.collect_test_results_unix('tests_tensorrt.xml', 'tests_python3_tensorrt_gpu.xml') } } } @@ -1012,21 +1012,6 @@ def test_unix_python3_integration_gpu() { }] } -def test_unix_caffe_gpu() { - return ['Caffe GPU': { - node(NODE_LINUX_GPU) { - ws('workspace/it-caffe') { - timeout(time: max_time, unit: 'MINUTES') { - utils.init_git() - utils.unpack_lib('gpu', mx_lib) - utils.docker_run('ubuntu_gpu_cu101', 'integrationtest_ubuntu_gpu_caffe', true) - utils.publish_test_coverage() - } - } - } - }] -} - def test_unix_cpp_package_gpu() { return ['cpp-package GPU Makefile': { node(NODE_LINUX_GPU) { @@ -1300,8 +1285,8 @@ def test_centos7_python3_cpu() { utils.docker_run('centos7_cpu', 'unittest_centos7_cpu', false) utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_unittest.xml', 'nosetests_python3_centos7_cpu_unittest.xml') - utils.collect_test_results_unix('nosetests_train.xml', 'nosetests_python3_centos7_cpu_train.xml') + utils.collect_test_results_unix('tests_unittest.xml', 'tests_python3_centos7_cpu_unittest.xml') + utils.collect_test_results_unix('tests_train.xml', 'tests_python3_centos7_cpu_train.xml') } } } @@ -1319,7 +1304,7 @@ def test_centos7_python3_gpu() { utils.docker_run('centos7_gpu_cu92', 'unittest_centos7_gpu', true) utils.publish_test_coverage() } finally { - utils.collect_test_results_unix('nosetests_gpu.xml', 'nosetests_python3_centos7_gpu.xml') + utils.collect_test_results_unix('tests_gpu.xml', 'tests_python3_centos7_gpu.xml') } } } @@ -1351,8 +1336,8 @@ def test_windows_python3_gpu() { unstash 'windows_package_gpu' powershell 'ci/windows/test_py3_gpu.ps1' } finally { - utils.collect_test_results_windows('nosetests_forward.xml', 'nosetests_gpu_forward_windows_python3_gpu.xml') - utils.collect_test_results_windows('nosetests_operator.xml', 'nosetests_gpu_operator_windows_python3_gpu.xml') + utils.collect_test_results_windows('tests_forward.xml', 'tests_gpu_forward_windows_python3_gpu.xml') + utils.collect_test_results_windows('tests_operator.xml', 'tests_gpu_operator_windows_python3_gpu.xml') } } } @@ -1370,8 +1355,8 @@ def test_windows_python3_gpu_mkldnn() { unstash 'windows_package_gpu_mkldnn' powershell 'ci/windows/test_py3_gpu.ps1' } finally { - utils.collect_test_results_windows('nosetests_forward.xml', 'nosetests_gpu_forward_windows_python3_gpu_mkldnn.xml') - utils.collect_test_results_windows('nosetests_operator.xml', 'nosetests_gpu_operator_windows_python3_gpu_mkldnn.xml') + utils.collect_test_results_windows('tests_forward.xml', 'tests_gpu_forward_windows_python3_gpu_mkldnn.xml') + utils.collect_test_results_windows('tests_operator.xml', 'tests_gpu_operator_windows_python3_gpu_mkldnn.xml') } } } @@ -1389,7 +1374,7 @@ def test_windows_python3_cpu() { unstash 'windows_package_cpu' powershell 'ci/windows/test_py3_cpu.ps1' } finally { - utils.collect_test_results_windows('nosetests_unittest.xml', 'nosetests_unittest_windows_python3_cpu.xml') + utils.collect_test_results_windows('tests_unittest.xml', 'tests_unittest_windows_python3_cpu.xml') } } } diff --git a/ci/jenkins/Jenkinsfile_centos_cpu b/ci/jenkins/Jenkinsfile_centos_cpu index e05d32633194..374be1c2edbc 100644 --- a/ci/jenkins/Jenkinsfile_centos_cpu +++ b/ci/jenkins/Jenkinsfile_centos_cpu @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_centos_gpu b/ci/jenkins/Jenkinsfile_centos_gpu index 31fad5ca8883..3c6c28dca6c0 100644 --- a/ci/jenkins/Jenkinsfile_centos_gpu +++ b/ci/jenkins/Jenkinsfile_centos_gpu @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_clang b/ci/jenkins/Jenkinsfile_clang index 1365b31b701d..953d4b43653d 100644 --- a/ci/jenkins/Jenkinsfile_clang +++ b/ci/jenkins/Jenkinsfile_clang @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_edge b/ci/jenkins/Jenkinsfile_edge index 9e2abf558dd2..857d081d8235 100644 --- a/ci/jenkins/Jenkinsfile_edge +++ b/ci/jenkins/Jenkinsfile_edge @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_miscellaneous b/ci/jenkins/Jenkinsfile_miscellaneous index 68d0de459897..a47e4c8f5cc2 100644 --- a/ci/jenkins/Jenkinsfile_miscellaneous +++ b/ci/jenkins/Jenkinsfile_miscellaneous @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { diff --git a/ci/jenkins/Jenkinsfile_sanity b/ci/jenkins/Jenkinsfile_sanity index ed4d16ec47db..48f55745b1d2 100644 --- a/ci/jenkins/Jenkinsfile_sanity +++ b/ci/jenkins/Jenkinsfile_sanity @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_tools b/ci/jenkins/Jenkinsfile_tools index 9af63aae1b2c..f9e17ed7a999 100644 --- a/ci/jenkins/Jenkinsfile_tools +++ b/ci/jenkins/Jenkinsfile_tools @@ -23,7 +23,7 @@ // A place to add tests scripts for supporting tools // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_unix_gpu b/ci/jenkins/Jenkinsfile_unix_gpu index 34ee5af1ce76..7742a654faa1 100644 --- a/ci/jenkins/Jenkinsfile_unix_gpu +++ b/ci/jenkins/Jenkinsfile_unix_gpu @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately @@ -59,12 +59,10 @@ core_logic: { custom_steps.test_unix_python3_integration_gpu(), custom_steps.test_unix_cpp_package_gpu(), custom_steps.test_unix_scala_gpu(), - custom_steps.test_unix_distributed_kvstore_gpu(), + // TODO(szha): fix and reenable the hanging issue. tracked in #18098 + // custom_steps.test_unix_distributed_kvstore_gpu(), custom_steps.test_unix_python3_gpu_no_tvm_op(), custom_steps.test_unix_capi_cpp_package(), - - // Disabled due to: https://github.com/apache/incubator-mxnet/issues/11407 - //custom_steps.test_unix_caffe_gpu() ]) } , diff --git a/ci/jenkins/Jenkinsfile_website_beta b/ci/jenkins/Jenkinsfile_website_beta index 9220052e9f0f..55c8ab837a9d 100644 --- a/ci/jenkins/Jenkinsfile_website_beta +++ b/ci/jenkins/Jenkinsfile_website_beta @@ -22,7 +22,7 @@ // This pipeline will publish to https://mxnet-beta.staged.apache.org/ // timeout in minutes -max_time = 180 +max_time = 240 node('restricted-utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_website_full b/ci/jenkins/Jenkinsfile_website_full index 39cc6f4e2dc9..ecf1f29ba574 100644 --- a/ci/jenkins/Jenkinsfile_website_full +++ b/ci/jenkins/Jenkinsfile_website_full @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('restricted-utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_website_full_pr b/ci/jenkins/Jenkinsfile_website_full_pr index 133c6c204964..9823fb33abe3 100644 --- a/ci/jenkins/Jenkinsfile_website_full_pr +++ b/ci/jenkins/Jenkinsfile_website_full_pr @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_website_mxnet_build b/ci/jenkins/Jenkinsfile_website_mxnet_build index a3c3330d0349..2acb1594fe0a 100644 --- a/ci/jenkins/Jenkinsfile_website_mxnet_build +++ b/ci/jenkins/Jenkinsfile_website_mxnet_build @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_website_nightly b/ci/jenkins/Jenkinsfile_website_nightly index 16c333e8df05..1bbe5bc2bade 100644 --- a/ci/jenkins/Jenkinsfile_website_nightly +++ b/ci/jenkins/Jenkinsfile_website_nightly @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('restricted-utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_windows_cpu b/ci/jenkins/Jenkinsfile_windows_cpu index 3de8f7d4330b..b6996645feb0 100644 --- a/ci/jenkins/Jenkinsfile_windows_cpu +++ b/ci/jenkins/Jenkinsfile_windows_cpu @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/jenkins/Jenkinsfile_windows_gpu b/ci/jenkins/Jenkinsfile_windows_gpu index 631d9e947002..b5db6654fcc4 100644 --- a/ci/jenkins/Jenkinsfile_windows_gpu +++ b/ci/jenkins/Jenkinsfile_windows_gpu @@ -21,7 +21,7 @@ // See documents at https://jenkins.io/doc/book/pipeline/jenkinsfile/ // timeout in minutes -max_time = 180 +max_time = 240 node('utility') { // Loading the utilities requires a node context unfortunately diff --git a/ci/safe_docker_run.py b/ci/safe_docker_run.py old mode 100755 new mode 100644 diff --git a/ci/test_docker_cache.py b/ci/test_docker_cache.py index aeb399ff6b45..81b315be4cff 100644 --- a/ci/test_docker_cache.py +++ b/ci/test_docker_cache.py @@ -270,8 +270,3 @@ def _assert_docker_build(lambda_func, expected_cache_hit_count: int, expected_ca assert output.count('Using cache') == expected_cache_hit_count, \ 'Expected {} "Using cache", got {}. Log:{}'.\ format(expected_cache_hit_count, output.count('Using cache'), output) - - -if __name__ == '__main__': - import nose - nose.main() diff --git a/ci/test_docker_login.py b/ci/test_docker_login.py index 6c989ade92ff..488295d9fa71 100644 --- a/ci/test_docker_login.py +++ b/ci/test_docker_login.py @@ -228,7 +228,3 @@ def test_main_default_argument_values(self, mock_login): with self.assertRaises(RuntimeError): main(["--secret-name", "name"]) - -if __name__ == '__main__': - import nose - nose.main() diff --git a/ci/test_safe_docker_run.py b/ci/test_safe_docker_run.py index 433d42e8b2ea..5b75c0eef4ba 100644 --- a/ci/test_safe_docker_run.py +++ b/ci/test_safe_docker_run.py @@ -420,8 +420,3 @@ def wait_for_container(name: str) -> bool: # The container should no longer exist assert get_container(container_name) is None - - -if __name__ == '__main__': - import nose - nose.main() diff --git a/ci/windows/test_py3_cpu.ps1 b/ci/windows/test_py3_cpu.ps1 index 8f520bb5b259..84f1da879eea 100644 --- a/ci/windows/test_py3_cpu.ps1 +++ b/ci/windows/test_py3_cpu.ps1 @@ -23,12 +23,12 @@ $env:MXNET_STORAGE_FALLBACK_LOG_VERBOSE=0 $env:MXNET_SUBGRAPH_VERBOSE=0 $env:MXNET_HOME=[io.path]::combine($PSScriptRoot, 'mxnet_home') -C:\Python37\Scripts\pip install -r tests\requirements.txt -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_unittest.xml tests\python\unittest +C:\Python37\Scripts\pip install -r ci\docker\install\requirements +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_unittest.xml tests\python\unittest if ($LastExitCode -ne 0) { Throw ("Error running unittest, python exited with status code " + ('{0:X}' -f $LastExitCode)) } -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_train.xml tests\python\train +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_train.xml tests\python\train if ($LastExitCode -ne 0) { Throw ("Error running train tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } # Adding this extra test since it's not possible to set env var on the fly in Windows. $env:MXNET_SAFE_ACCUMULATION=1 -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_unittest.xml tests\python\unittest\test_operator.py:test_norm +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_unittest.xml --cov-append tests\python\unittest\test_operator.py::test_norm if ($LastExitCode -ne 0) { Throw ("Error running unittest, python exited with status code " + ('{0:X}' -f $LastExitCode)) } diff --git a/ci/windows/test_py3_gpu.ps1 b/ci/windows/test_py3_gpu.ps1 index 0ce3d953d486..e83b865c1d5c 100644 --- a/ci/windows/test_py3_gpu.ps1 +++ b/ci/windows/test_py3_gpu.ps1 @@ -23,16 +23,18 @@ $env:MXNET_STORAGE_FALLBACK_LOG_VERBOSE=0 $env:MXNET_SUBGRAPH_VERBOSE=0 $env:MXNET_HOME=[io.path]::combine($PSScriptRoot, 'mxnet_home') -C:\Python37\Scripts\pip install -r tests\requirements.txt -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_unittest.xml tests\python\unittest +C:\Python37\Scripts\pip install -r ci\docker\install\requirements +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_unittest.xml tests\python\unittest if ($LastExitCode -ne 0) { Throw ("Error running unittest, python exited with status code " + ('{0:X}' -f $LastExitCode)) } -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_operator.xml tests\python\gpu\test_operator_gpu.py +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_operator.xml tests\python\gpu\test_operator_gpu.py if ($LastExitCode -ne 0) { Throw ("Error running tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_forward.xml tests\python\gpu\test_forward.py +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_forward.xml tests\python\gpu\test_forward.py if ($LastExitCode -ne 0) { Throw ("Error running tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_train.xml tests\python\train +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_train.xml tests\python\train if ($LastExitCode -ne 0) { Throw ("Error running tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } # Adding this extra test since it's not possible to set env var on the fly in Windows. $env:MXNET_SAFE_ACCUMULATION=1 -C:\Python37\python.exe -m nose -v --with-timer --timer-ok 1 --timer-warning 15 --timer-filter warning,error --with-xunit --xunit-file nosetests_operator.xml tests\python\gpu\test_operator_gpu.py:test_norm +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_operator.xml --cov-append tests\python\gpu\test_operator_gpu.py::test_norm if ($LastExitCode -ne 0) { Throw ("Error running tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } +C:\Python37\python.exe -m pytest -v --durations=50 --cov-report xml:tests_tvm_op.xml tests\python\gpu\test_tvm_op_gpu.py +if ($LastExitCode -ne 0) { Throw ("Error running TVM op tests, python exited with status code " + ('{0:X}' -f $LastExitCode)) } diff --git a/conftest.py b/conftest.py new file mode 100644 index 000000000000..dad6854ee30c --- /dev/null +++ b/conftest.py @@ -0,0 +1,226 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. +"""conftest.py contains configuration for pytest. + +Configuration file for tests in tests/ and scripts/ folders. + +Note that fixtures of higher-scoped fixtures (such as ``session``) are +instantiated before lower-scoped fixtures (such as ``function``). + +""" + +import logging +import os +import random + +import pytest + + +def pytest_sessionfinish(session, exitstatus): + if exitstatus == 5: # Don't fail if no tests were run + session.exitstatus = 0 + + +# * Random seed setup +def pytest_configure(): + """Pytest configuration hook to help reproduce test segfaults + + Sets and outputs rng seeds. + + The segfault-debug procedure on a module called test_module.py is: + + 1. run "pytest --verbose test_module.py". A seg-faulting output might be: + + [INFO] np, mx and python random seeds = 4018804151 + test_module.test1 ... ok + test_module.test2 ... Illegal instruction (core dumped) + + 2. Copy the module-starting seed into the next command, then run: + + MXNET_MODULE_SEED=4018804151 pytest --log-level=DEBUG --verbose test_module.py + + Output might be: + + [WARNING] **** module-level seed is set: all tests running deterministically **** + [INFO] np, mx and python random seeds = 4018804151 + test_module.test1 ... [DEBUG] np and mx random seeds = 3935862516 + ok + test_module.test2 ... [DEBUG] np and mx random seeds = 1435005594 + Illegal instruction (core dumped) + + 3. Copy the segfaulting-test seed into the command: + MXNET_TEST_SEED=1435005594 pytest --log-level=DEBUG --verbose test_module.py:test2 + Output might be: + + [INFO] np, mx and python random seeds = 2481884723 + test_module.test2 ... [DEBUG] np and mx random seeds = 1435005594 + Illegal instruction (core dumped) + + 3. Finally reproduce the segfault directly under gdb (might need additional os packages) + by editing the bottom of test_module.py to be + + if __name__ == '__main__': + logging.getLogger().setLevel(logging.DEBUG) + test2() + + MXNET_TEST_SEED=1435005594 gdb -ex r --args python test_module.py + + 4. When finished debugging the segfault, remember to unset any exported MXNET_ seed + variables in the environment to return to non-deterministic testing (a good thing). + """ + + module_seed_str = os.getenv('MXNET_MODULE_SEED') + if module_seed_str is None: + seed = random.randint(0, 2**31-1) + else: + seed = int(module_seed_str) + logging.warning('*** module-level seed is set: ' + 'all tests running deterministically ***') + logging.info('Setting module np/mx/python random seeds, ' + 'use MXNET_MODULE_SEED={} to reproduce.'.format(seed)) + + random.seed(seed) + try: + import numpy as np + import mxnet as mx + np.random.seed(seed) + mx.random.seed(seed) + except: + logging.warning('Unable to import numpy/mxnet. Skipping conftest.') + + # The MXNET_TEST_SEED environment variable will override MXNET_MODULE_SEED for tests with + # the 'with_seed()' decoration. Inform the user of this once here at the module level. + if os.getenv('MXNET_TEST_SEED') is not None: + logging.warning('*** test-level seed set: all "@with_seed()" ' + 'tests run deterministically ***') + + +@pytest.hookimpl(tryfirst=True, hookwrapper=True) +def pytest_runtest_makereport(item, call): + """Make test outcome available to fixture. + + https://docs.pytest.org/en/latest/example/simple.html#making-test-result-information-available-in-fixtures + """ + # execute all other hooks to obtain the report object + outcome = yield + rep = outcome.get_result() + + # set a report attribute for each phase of a call, which can + # be "setup", "call", "teardown" + setattr(item, "rep_" + rep.when, rep) + + +@pytest.fixture(scope='function', autouse=True) +def function_scope_seed(request): + """A function scope fixture that manages rng seeds. + + This fixture automatically initializes the python, numpy and mxnet random + number generators randomly on every test run. + + def test_ok_with_random_data(): + ... + + To fix the seed used for a test case mark the test function with the + desired seed: + + @pytest.mark.seed(1) + def test_not_ok_with_random_data(): + '''This testcase actually works.''' + assert 17 == random.randint(0, 100) + + When a test fails, the fixture outputs the seed used. The user can then set + the environment variable MXNET_TEST_SEED to the value reported, then rerun + the test with: + + pytest --verbose -s -k + + To run a test repeatedly, install pytest-repeat and add the --count argument: + + pip install pytest-repeat + pytest --verbose -s -k --count 1000 + + """ + + seed = request.node.get_closest_marker('seed') + env_seed_str = os.getenv('MXNET_TEST_SEED') + + if seed is not None: + seed = seed.args[0] + assert isinstance(seed, int) + elif env_seed_str is not None: + seed = int(env_seed_str) + else: + seed = random.randint(0, 2**31-1) + + random.seed(seed) + try: + import numpy as np + import mxnet as mx + post_test_state = np.random.get_state() + np.random.seed(seed) + mx.random.seed(seed) + except: + logging.warning('Unable to import numpy/mxnet. Skipping seeding for numpy/mxnet.') + np = None + + seed_message = ('np/mx/python random seeds are set to ' + '{}, use MXNET_TEST_SEED={} to reproduce.') + seed_message = seed_message.format(seed, seed) + + # Always log seed on DEBUG log level. This makes sure we can find out the + # value of the seed even if the test case causes a segfault and subsequent + # teardown code is not run. + logging.debug(seed_message) + + yield # run the test + + try: + import mxnet as mx + mx.nd.waitall() + except: + logging.warning('Unable to import mxnet. Skipping for mxnet engine.') + + if request.node.rep_setup.failed: + logging.info("Setting up a test failed: {}", request.node.nodeid) + elif request.node.rep_call.outcome == 'failed': + # Either request.node.rep_setup.failed or request.node.rep_setup.passed + # should be True + assert request.node.rep_setup.passed + # On failure also log seed on INFO log level + logging.info(seed_message) + + if np: + np.random.set_state(post_test_state) + + +# * Shared test fixtures +@pytest.fixture(params=[True, False]) +def hybridize(request): + return request.param + +@pytest.fixture(autouse=True) +def doctest(doctest_namespace): + try: + import numpy as np + import mxnet as mx + doctest_namespace['np'] = np + doctest_namespace['mx'] = mx + doctest_namespace['gluon'] = mx.gluon + except: + logging.warning('Unable to import numpy/mxnet. Skipping conftest.') + import doctest + doctest.ELLIPSIS_MARKER = '-etc-' diff --git a/contrib/clojure-package/examples/captcha/gen_captcha.py b/contrib/clojure-package/examples/captcha/gen_captcha.py old mode 100755 new mode 100644 diff --git a/docker/install/python.sh b/docker/install/python.sh index ba71246babbf..d49b500d843c 100755 --- a/docker/install/python.sh +++ b/docker/install/python.sh @@ -19,10 +19,9 @@ # install libraries for mxnet's python package on ubuntu -apt-get update && apt-get install -y python-dev python3-dev +apt-get update && apt-get install -y python3-dev # the version of the pip shipped with ubuntu may be too lower, install a recent version here -cd /tmp && wget https://bootstrap.pypa.io/get-pip.py && python3 get-pip.py && python2 get-pip.py +cd /tmp && wget https://bootstrap.pypa.io/get-pip.py && python3 get-pip.py -pip2 install nose pylint numpy nose-timer requests Pillow -pip3 install nose pylint numpy nose-timer requests Pillow +pip3 install pylint numpy requests Pillow pytest==5.3.2 pytest-env==0.6.2 pytest-cov==2.8.1 pytest-xdist==1.31.0 diff --git a/docs/static_site/src/pages/get_started/build_from_source.md b/docs/static_site/src/pages/get_started/build_from_source.md index 1dfa95a82ade..ae391e4fe67e 100644 --- a/docs/static_site/src/pages/get_started/build_from_source.md +++ b/docs/static_site/src/pages/get_started/build_from_source.md @@ -221,7 +221,7 @@ make -j"$(nproc)" ``` - Run test_nccl.py script as follows. The test should complete. It does not produce any output. ``` bash -nosetests --verbose tests/python/gpu/test_nccl.py +pytest --verbose tests/python/gpu/test_nccl.py ``` **Recommendation to get the best performance out of NCCL:** diff --git a/example/image-classification/__init__.py b/example/image-classification/__init__.py old mode 100755 new mode 100644 diff --git a/example/image-classification/benchmark.py b/example/image-classification/benchmark.py old mode 100755 new mode 100644 diff --git a/example/image-classification/benchmark_score.py b/example/image-classification/benchmark_score.py old mode 100755 new mode 100644 diff --git a/example/image-classification/common/data.py b/example/image-classification/common/data.py old mode 100755 new mode 100644 diff --git a/example/image-classification/common/fit.py b/example/image-classification/common/fit.py old mode 100755 new mode 100644 diff --git a/example/image-classification/fine-tune.py b/example/image-classification/fine-tune.py old mode 100755 new mode 100644 diff --git a/example/image-classification/score.py b/example/image-classification/score.py old mode 100755 new mode 100644 diff --git a/example/image-classification/symbols/alexnet.py b/example/image-classification/symbols/alexnet.py old mode 100755 new mode 100644 diff --git a/example/image-classification/symbols/resnet-v1.py b/example/image-classification/symbols/resnet-v1.py old mode 100755 new mode 100644 diff --git a/example/image-classification/symbols/resnetv1.py b/example/image-classification/symbols/resnetv1.py old mode 100755 new mode 100644 diff --git a/example/image-classification/test_score.py b/example/image-classification/test_score.py old mode 100755 new mode 100644 index 8fbac68c9064..58c5c66a7f1f --- a/example/image-classification/test_score.py +++ b/example/image-classification/test_score.py @@ -25,40 +25,40 @@ import mxnet as mx from common import find_mxnet, modelzoo from score import score +import pytest -VAL_DATA='data/val-5k-256.rec' -def download_data(): - return mx.test_utils.download( - 'http://data.mxnet.io/data/val-5k-256.rec', VAL_DATA) +@pytest.fixture(scope="session") +def imagenet_val_5k_settings(): + mx.test_utils.download( + 'http://data.mxnet.io/data/val-5k-256.rec', 'data/val-5k-256.rec') + num_gpus = mx.context.num_gpus() + assert num_gpus > 0 + gpus = ','.join(map(str, range(num_gpus))) + batch_size = 16 * num_gpus + kwargs = {'gpus':gpus, 'batch_size':batch_size, 'max_num_examples':500} + return 'data/val-5k-256.rec', kwargs -def test_imagenet1k_resnet(**kwargs): +def test_imagenet1k_resnet(imagenet_val_5k_settings): + imagenet_val_5k, kwargs = imagenet_val_5k_settings models = ['imagenet1k-resnet-50', 'imagenet1k-resnet-152'] accs = [.77, .78] for (m, g) in zip(models, accs): acc = mx.metric.create('acc') - (speed,) = score(model=m, data_val=VAL_DATA, + (speed,) = score(model=m, data_val=imagenet_val_5k, rgb_mean='0,0,0', metrics=acc, **kwargs) r = acc.get()[1] print('Tested %s, acc = %f, speed = %f img/sec' % (m, r, speed)) assert r > g and r < g + .1 -def test_imagenet1k_inception_bn(**kwargs): +def test_imagenet1k_inception_bn(imagenet_val_5k_settings): + imagenet_val_5k, kwargs = imagenet_val_5k_settings acc = mx.metric.create('acc') m = 'imagenet1k-inception-bn' g = 0.75 (speed,) = score(model=m, - data_val=VAL_DATA, + data_val=imagenet_val_5k, rgb_mean='123.68,116.779,103.939', metrics=acc, **kwargs) r = acc.get()[1] print('Tested %s acc = %f, speed = %f img/sec' % (m, r, speed)) assert r > g and r < g + .1 -if __name__ == '__main__': - num_gpus = mx.context.num_gpus() - assert num_gpus > 0 - batch_size = 16 * num_gpus - gpus = ','.join(map(str, range(num_gpus))) - kwargs = {'gpus':gpus, 'batch_size':batch_size, 'max_num_examples':500} - download_data() - test_imagenet1k_resnet(**kwargs) - test_imagenet1k_inception_bn(**kwargs) diff --git a/example/image-classification/train_cifar10.py b/example/image-classification/train_cifar10.py old mode 100755 new mode 100644 diff --git a/example/image-classification/train_imagenet.py b/example/image-classification/train_imagenet.py old mode 100755 new mode 100644 diff --git a/example/image-classification/train_mnist.py b/example/image-classification/train_mnist.py old mode 100755 new mode 100644 diff --git a/example/neural_collaborative_filtering/ci.py b/example/neural_collaborative_filtering/ci.py index 81f1a27e606b..1bf5b27cae32 100644 --- a/example/neural_collaborative_filtering/ci.py +++ b/example/neural_collaborative_filtering/ci.py @@ -14,13 +14,13 @@ # KIND, either express or implied. See the License for the # specific language governing permissions and limitations # under the License. -# + import mxnet as mx from core.model import get_model def test_model(): def test_ncf(model_type): - net = get_model(model_type=model_type, factor_size_mlp=128, factor_size_gmf=64, + net = get_model(model_type=model_type, factor_size_mlp=128, factor_size_gmf=64, model_layers=[256, 128, 64], num_hidden=1, max_user=138493, max_item=26744) mod = mx.module.Module(net, context=mx.cpu(), data_names=['user', 'item'], label_names=['softmax_label']) provide_data = [mx.io.DataDesc(name='item', shape=((1,))), @@ -58,7 +58,3 @@ def test_ncf(model_type): for model_type in ['neumf', 'mlp', 'gmf']: test_ncf(model_type) -if __name__ == "__main__": - import nose - nose.runmodule() - diff --git a/example/reinforcement-learning/dqn/dqn_demo.py b/example/reinforcement-learning/dqn/dqn_demo.py old mode 100755 new mode 100644 diff --git a/example/reinforcement-learning/dqn/dqn_run_test.py b/example/reinforcement-learning/dqn/dqn_run_test.py old mode 100755 new mode 100644 diff --git a/example/ssd/data/demo/download_demo_images.py b/example/ssd/data/demo/download_demo_images.py old mode 100755 new mode 100644 diff --git a/example/ssd/dataset/pycocotools/__init__.py b/example/ssd/dataset/pycocotools/__init__.py old mode 100755 new mode 100644 diff --git a/example/ssd/dataset/pycocotools/coco.py b/example/ssd/dataset/pycocotools/coco.py old mode 100755 new mode 100644 diff --git a/example/ssd/demo.py b/example/ssd/demo.py old mode 100755 new mode 100644 diff --git a/example/ssd/tools/prepare_dataset.py b/example/ssd/tools/prepare_dataset.py old mode 100755 new mode 100644 diff --git a/example/ssd/train.py b/example/ssd/train.py old mode 100755 new mode 100644 diff --git a/ci/docker/install/ubuntu_onnx.sh b/pytest.ini old mode 100755 new mode 100644 similarity index 55% rename from ci/docker/install/ubuntu_onnx.sh rename to pytest.ini index 44d6b9ed52dc..52ad95f88ed3 --- a/ci/docker/install/ubuntu_onnx.sh +++ b/pytest.ini @@ -1,5 +1,3 @@ -#!/usr/bin/env bash - # Licensed to the Apache Software Foundation (ASF) under one # or more contributor license agreements. See the NOTICE file # distributed with this work for additional information @@ -17,18 +15,16 @@ # specific language governing permissions and limitations # under the License. -###################################################################### -# This script installs ONNX for Python along with all required dependencies -# on a Ubuntu Machine. -# Tested on Ubuntu 16.04 distro. -###################################################################### - -set -e -set -x +[pytest] +markers = + seed: set the python, numpy and mxnet random seeds to a specified value for test reproducibility + serial: mark a test that requires more resources to run that are thus only suitable for serial run. + remote_required: mark a test that requires internet access. + gpu: mark a test that requires GPU. + integration: mark an integration test + onnx_coverage: ONNX coverage test -echo "Installing libprotobuf-dev and protobuf-compiler ..." -apt-get update || true -apt-get install -y libprotobuf-dev protobuf-compiler +env = + MXNET_HOME=tests/data -echo "Installing pytest, pytest-cov, protobuf, Pillow, ONNX and tabulate ..." -pip3 install pytest==3.6.3 pytest-cov==2.5.1 protobuf==3.5.2 onnx==1.3.0 Pillow==5.0.0 tabulate==0.7.5 +timeout = 1200 diff --git a/python/README.md b/python/README.md index 148188537f48..e5d2faa86575 100644 --- a/python/README.md +++ b/python/README.md @@ -25,14 +25,14 @@ To install MXNet Python package, visit MXNet [Install Instruction](https://mxnet ## Running the unit tests -For running unit tests, you will need the [nose PyPi package](https://pypi.python.org/pypi/nose). To install: +For running unit tests, you will need the [pytest PyPi package](https://pypi.python.org/pypi/pytest). To install: ```bash -pip install --upgrade nose +pip install --upgrade pytest ``` -Once ```nose``` is installed, run the following from MXNet root directory (please make sure the installation path of ```nosetests``` is included in your ```$PATH``` environment variable): +Once ```pytest``` is installed, run the following from MXNet root directory (please make sure the installation path of ```pytest``` is included in your ```$PATH``` environment variable): ``` -nosetests tests/python/unittest -nosetests tests/python/train +pytest tests/python/unittest +pytest tests/python/train ``` diff --git a/python/mxnet/_ffi/base.py b/python/mxnet/_ffi/base.py index be68d20c53e2..df95b95115a5 100644 --- a/python/mxnet/_ffi/base.py +++ b/python/mxnet/_ffi/base.py @@ -69,18 +69,3 @@ def c_array(ctype, values): Created ctypes array """ return (ctype * len(values))(*values) - - -def decorate(func, fwrapped): - """A wrapper call of decorator package, differs to call time - - Parameters - ---------- - func : function - The original function - - fwrapped : function - The wrapped function - """ - import decorator - return decorator.decorate(func, fwrapped) diff --git a/python/mxnet/contrib/amp/amp.py b/python/mxnet/contrib/amp/amp.py old mode 100755 new mode 100644 diff --git a/python/mxnet/contrib/amp/loss_scaler.py b/python/mxnet/contrib/amp/loss_scaler.py old mode 100755 new mode 100644 diff --git a/python/mxnet/image/detection.py b/python/mxnet/image/detection.py index 52c94684912a..e62fb67ce88b 100644 --- a/python/mxnet/image/detection.py +++ b/python/mxnet/image/detection.py @@ -702,7 +702,7 @@ def _check_valid_label(self, label): def _estimate_label_shape(self): """Helper function to estimate label shape""" - max_count = 0 + max_count, label = 0, None self.reset() try: while True: @@ -712,7 +712,7 @@ def _estimate_label_shape(self): except StopIteration: pass self.reset() - return (max_count, label.shape[1]) + return (max_count, label.shape[1] if label is not None else 5) def _parse_label(self, label): """Helper function to parse object detection label. diff --git a/python/mxnet/initializer.py b/python/mxnet/initializer.py old mode 100755 new mode 100644 diff --git a/python/mxnet/module/executor_group.py b/python/mxnet/module/executor_group.py old mode 100755 new mode 100644 diff --git a/python/mxnet/optimizer/optimizer.py b/python/mxnet/optimizer/optimizer.py old mode 100755 new mode 100644 diff --git a/python/mxnet/test_utils.py b/python/mxnet/test_utils.py old mode 100755 new mode 100644 index 6a2c2456f05f..6129d690d700 --- a/python/mxnet/test_utils.py +++ b/python/mxnet/test_utils.py @@ -756,24 +756,6 @@ def assert_exception(f, exception_type, *args, **kwargs): except exception_type: return -def retry(n): - """Retry n times before failing for stochastic test cases.""" - assert n > 0 - def decorate(f): - """Decorate a test case.""" - def wrapper(*args, **kwargs): - """Wrapper for tests function.""" - for _ in range(n): - try: - f(*args, **kwargs) - except AssertionError as e: - err = e - continue - return - raise err - return wrapper - return decorate - def simple_forward(sym, ctx=None, is_train=False, **inputs): """A simple forward function for a symbol. diff --git a/python/setup.py b/python/setup.py index ccfccb3f3f74..a040cbbf74e2 100644 --- a/python/setup.py +++ b/python/setup.py @@ -30,7 +30,7 @@ else: from setuptools import setup from setuptools.extension import Extension - kwargs = {'install_requires': ['numpy>1.16.0,<2.0.0', 'requests>=2.20.0,<3', 'graphviz<0.9.0,>=0.8.1'], 'zip_safe': False} + kwargs = {'install_requires': ['numpy>=1.17', 'requests>=2.20.0,<3', 'graphviz<0.9.0,>=0.8.1'], 'zip_safe': False} with_cython = False if '--with-cython' in sys.argv: diff --git a/snapcraft.yaml b/snapcraft.yaml deleted file mode 100644 index 896db372110d..000000000000 --- a/snapcraft.yaml +++ /dev/null @@ -1,79 +0,0 @@ -# Licensed to the Apache Software Foundation (ASF) under one -# or more contributor license agreements. See the NOTICE file -# distributed with this work for additional information -# regarding copyright ownership. The ASF licenses this file -# to you under the Apache License, Version 2.0 (the -# "License"); you may not use this file except in compliance -# with the License. You may obtain a copy of the License at -# -# http://www.apache.org/licenses/LICENSE-2.0 -# -# Unless required by applicable law or agreed to in writing, -# software distributed under the License is distributed on an -# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY -# KIND, either express or implied. See the License for the -# specific language governing permissions and limitations -# under the License. - -name: mxnet -version: '2.0.0' -summary: MXNet is a deep learning framework designed for efficiency and flexibility. -description: | - MXNet is a deep learning framework designed for both efficiency and - flexibility. It allows you to mix the flavours of symbolic programming and - imperative programming to maximize efficiency and productivity. In its core, - a dynamic dependency scheduler that automatically parallelizes both symbolic - and imperative operations on the fly. A graph optimization layer on top of - that makes symbolic execution fast and memory efficient. The library is - portable and lightweight, and it scales to multiple GPUs and multiple machines. - -grade: stable -confinement: strict - -apps: - python: - command: snap.python - -parts: - mxnet: - source: . - plugin: make - build-packages: - - build-essential - - libatlas-base-dev - - libopencv-dev - stage-packages: - - libatlas3-base - - libopencv-calib3d2.4v5 - - libopencv-core2.4v5 - - libopencv-highgui2.4v5 - - libopencv-imgproc2.4v5 - - libopencv-ml2.4v5 - - libopencv-objdetect2.4v5 - prepare: | - cp make/config.mk . - build: | - make - install: | - cp -r bin $SNAPCRAFT_PART_INSTALL/ - cp -r lib $SNAPCRAFT_PART_INSTALL/ - - mxnet-ubuntu-python: - plugin: python - python-version: python2 - source: ./python - stage-packages: - - python-numpy - python-packages: - - graphviz - - Jupyter - after: [mxnet] - - python-wrapper: - plugin: dump - source: . - stage: - - snap.python - prime: - - snap.python - diff --git a/tests/README.md b/tests/README.md index de5d8107a790..b59335ea1593 100644 --- a/tests/README.md +++ b/tests/README.md @@ -68,7 +68,7 @@ Ninja is a build tool (like make) that prioritizes building speed. If you will b ``` An example for running python tests would be ``` -ci/build.py --platform build_ubuntu_cpu_mkldnn /work/runtime_functions.sh unittest_ubuntu_python3_cpu PYTHONPATH=./python/ nosetests-2.7 tests/python/unittest +ci/build.py --platform build_ubuntu_cpu_mkldnn /work/runtime_functions.sh unittest_ubuntu_python3_cpu PYTHONPATH=./python/ pytest tests/python/unittest ``` diff --git a/tests/jenkins/run_test.sh b/tests/jenkins/run_test.sh index 5ded74291f25..48bb4da53fc4 100755 --- a/tests/jenkins/run_test.sh +++ b/tests/jenkins/run_test.sh @@ -42,16 +42,10 @@ export MXNET_ENGINE_INFO=false export PYTHONPATH=$(pwd)/python echo "BUILD python_test" -nosetests --verbose tests/python/unittest || exit -1 -nosetests --verbose tests/python/gpu/test_operator_gpu.py || exit -1 -nosetests --verbose tests/python/gpu/test_forward.py || exit -1 -nosetests --verbose tests/python/train || exit -1 - -echo "BUILD python3_test" -nosetests3 --verbose tests/python/unittest || exit -1 -nosetests3 --verbose tests/python/gpu/test_operator_gpu.py || exit -1 -nosetests3 --verbose tests/python/gpu/test_forward.py || exit -1 -nosetests3 --verbose tests/python/train || exit -1 +pytest --verbose tests/python/unittest || exit -1 +pytest --verbose tests/python/gpu/test_operator_gpu.py || exit -1 +pytest --verbose tests/python/gpu/test_forward.py || exit -1 +pytest --verbose tests/python/train || exit -1 echo "BUILD scala_test" export PATH=$PATH:/opt/apache-maven/bin diff --git a/tests/jenkins/run_test_amzn_linux_gpu.sh b/tests/jenkins/run_test_amzn_linux_gpu.sh index 57d9c7884088..a257b9684ba0 100755 --- a/tests/jenkins/run_test_amzn_linux_gpu.sh +++ b/tests/jenkins/run_test_amzn_linux_gpu.sh @@ -53,12 +53,8 @@ export MXNET_ENGINE_INFO=false export PYTHONPATH=${PWD}/python echo "BUILD python_test" -nosetests --verbose tests/python/unittest -nosetests --verbose tests/python/train - -echo "BUILD python3_test" -nosetests3 --verbose tests/python/unittest -nosetests3 --verbose tests/python/train +pytest --verbose tests/python/unittest +pytest --verbose tests/python/train #echo "BUILD julia_test" #export MXNET_HOME="${PWD}" diff --git a/tests/jenkins/run_test_ubuntu.sh b/tests/jenkins/run_test_ubuntu.sh index 0459d2cc8ec5..9c3d3c55c852 100755 --- a/tests/jenkins/run_test_ubuntu.sh +++ b/tests/jenkins/run_test_ubuntu.sh @@ -54,16 +54,10 @@ make -j$(nproc) export PYTHONPATH=${PWD}/python echo "BUILD python_test" -nosetests --verbose tests/python/unittest || exit 1 -nosetests --verbose tests/python/gpu/test_operator_gpu.py || exit 1 -nosetests --verbose tests/python/gpu/test_forward.py || exit 1 -nosetests --verbose tests/python/train || exit 1 - -echo "BUILD python3_test" -nosetests3 --verbose tests/python/unittest || exit 1 -nosetests3 --verbose tests/python/gpu/test_operator_gpu.py || exit 1 -nosetests3 --verbose tests/python/gpu/test_forward.py || exit 1 -nosetests3 --verbose tests/python/train || exit 1 +pytest --verbose tests/python/unittest || exit 1 +pytest --verbose tests/python/gpu/test_operator_gpu.py || exit 1 +pytest --verbose tests/python/gpu/test_forward.py || exit 1 +pytest --verbose tests/python/train || exit 1 echo "BUILD scala_test" export PATH=$PATH:/opt/apache-maven/bin diff --git a/tests/nightly/broken_link_checker_test/test_broken_links.py b/tests/nightly/broken_link_checker_test/test_broken_links.py old mode 100755 new mode 100644 diff --git a/tests/nightly/compilation_warnings/process_output.py b/tests/nightly/compilation_warnings/process_output.py old mode 100755 new mode 100644 diff --git a/tests/nightly/dist_device_sync_kvstore.py b/tests/nightly/dist_device_sync_kvstore.py index 26e665d414a1..a69687605798 100644 --- a/tests/nightly/dist_device_sync_kvstore.py +++ b/tests/nightly/dist_device_sync_kvstore.py @@ -127,5 +127,6 @@ def check_trainer_kv_update(update_on_kv): if __name__ == "__main__": test_sync_init() - test_sync_push_pull() + # TODO(szha): disabled due to repeated failures. tracked in #18098 + # test_sync_push_pull() test_gluon_trainer_type() diff --git a/tests/nightly/estimator/test_estimator_cnn.py b/tests/nightly/estimator/test_estimator_cnn.py index af519536dbed..0d113cdf4984 100644 --- a/tests/nightly/estimator/test_estimator_cnn.py +++ b/tests/nightly/estimator/test_estimator_cnn.py @@ -155,7 +155,3 @@ def test_estimator_gpu(): assert acc.get()[1] > 0.80 - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/nightly/estimator/test_sentiment_rnn.py b/tests/nightly/estimator/test_sentiment_rnn.py index ab124ba95db3..367c69b88a0b 100644 --- a/tests/nightly/estimator/test_sentiment_rnn.py +++ b/tests/nightly/estimator/test_sentiment_rnn.py @@ -280,7 +280,3 @@ def test_estimator_gpu(): assert acc.get()[1] > 0.70 - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/nightly/test_distributed_training-gpu.sh b/tests/nightly/test_distributed_training-gpu.sh index 40b6e1464a0d..319c031087fd 100755 --- a/tests/nightly/test_distributed_training-gpu.sh +++ b/tests/nightly/test_distributed_training-gpu.sh @@ -27,14 +27,14 @@ test_kvstore() { "-n 4 --launcher local python3 dist_device_sync_kvstore.py" "-n 4 --launcher local python3 dist_device_sync_kvstore_custom.py" "--p3 -n 4 --launcher local python3 dist_device_sync_kvstore_custom.py" - "-n 4 --launcher local python3 dist_sync_kvstore.py --type=init_gpu" + "-n 4 --launcher local python3 dist_sync_kvstore.py --type=init_gpu" ) for arg in "${test_args[@]}"; do python3 ../../tools/launch.py $arg if [ $? -ne 0 ]; then return $? - fi + fi done } @@ -50,4 +50,4 @@ test_horovod() { test_kvstore test_horovod -exit $errors \ No newline at end of file +exit $errors diff --git a/tests/nightly/test_large_array.py b/tests/nightly/test_large_array.py index 5fb0ff81da6b..0f0b373409b9 100644 --- a/tests/nightly/test_large_array.py +++ b/tests/nightly/test_large_array.py @@ -28,7 +28,6 @@ from mxnet.test_utils import rand_ndarray, assert_almost_equal, rand_coord_2d, default_context, check_symbolic_forward, create_2d_tensor from mxnet import gluon, nd from common import with_seed, with_post_test_cleanup -from nose.tools import with_setup import unittest # dimension constants @@ -469,7 +468,7 @@ def check_col2im(): assert res.shape[2] == 2 assert res.shape[3] == 2 assert res.shape[4] == 1 - + def check_embedding(): data = nd.random_normal(shape=(LARGE_TENSOR_SHAPE, 1)) weight = nd.random_normal(shape=(LARGE_TENSOR_SHAPE, 1)) @@ -480,7 +479,7 @@ def check_embedding(): assert out.shape[0] == LARGE_TENSOR_SHAPE assert out.shape[1] == 1 - + def check_spatial_transformer(): data = nd.random_normal(shape=(2, 2**29, 1, 6)) loc = nd.random_normal(shape=(2, 6)) @@ -495,7 +494,7 @@ def check_spatial_transformer(): assert res.shape[1] == 536870912 assert res.shape[2] == 2 assert res.shape[3] == 6 - + def check_ravel(): data = nd.random_normal(shape=(2, LARGE_TENSOR_SHAPE)) shape = (2, 10) @@ -530,7 +529,7 @@ def check_multi_lars(): # Trigger lazy evaluation of the output NDArray and ensure that it has been filled assert type(out[0, 0].asscalar()).__name__ == 'float32' - + def check_rnn(): data = nd.random_normal(shape=(RNN_LARGE_TENSOR, 4, 4)) parameters_relu_tanh = nd.random_normal(shape=(7,)) @@ -547,10 +546,10 @@ def check_rnn(): out_relu = nd.RNN(data=data, parameters=parameters_relu_tanh, state=state, mode=mode_relu, state_size=state_size, num_layers=num_layers) - + out_tanh = nd.RNN(data=data, parameters=parameters_relu_tanh, state=state, mode=mode_tanh, state_size=state_size, num_layers=num_layers) - + out_lstm = nd.RNN(data=data, parameters=parameters_lstm, state=state, mode=mode_lstm, state_cell=state_cell, state_size=state_size, num_layers=num_layers) @@ -1546,7 +1545,7 @@ def check_logical_xor(a, b): def create_input_for_rounding_ops(): # Creates an vector with values (-LARGE_X/2 .... -2, -1, 0, 1, 2, .... , LARGE_X/2-1) # then divides each element by 2 i.e (-LARGE_X/4 .... -1, -0.5, 0, 0.5, 1, .... , LARGE_X/4-1) - # and finally broadcasts to + # and finally broadcasts to inp = nd.arange(-LARGE_X//2, LARGE_X//2, dtype=np.float64).reshape(1, LARGE_X) inp = inp/2 inp = nd.broadcast_to(inp, (SMALL_Y, LARGE_X)) @@ -1559,7 +1558,7 @@ def assert_correctness_of_rounding_ops(output, mid, expected_vals): for i in range(len(output_idx_to_inspect)): assert output[1][output_idx_to_inspect[i]] == expected_vals[i] - # TODO(access2rohit): merge similar tests in large vector and array into one file. + # TODO(access2rohit): merge similar tests in large vector and array into one file. def check_rounding_ops(): x = create_input_for_rounding_ops() def check_ceil(): @@ -1819,7 +1818,3 @@ def test_sparse_dot(): assert out.asnumpy()[0][0] == 2 assert out.shape == (2, 2) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/nightly/test_large_vector.py b/tests/nightly/test_large_vector.py index bbad75627769..57fecaafc0ac 100644 --- a/tests/nightly/test_large_vector.py +++ b/tests/nightly/test_large_vector.py @@ -28,7 +28,6 @@ from mxnet.test_utils import rand_ndarray, assert_almost_equal, rand_coord_2d, create_vector from mxnet import gluon, nd from tests.python.unittest.common import with_seed -from nose.tools import with_setup import unittest # dimension constants @@ -370,7 +369,7 @@ def check_slice_axis(): def check_gather(): arr = mx.nd.ones(LARGE_X) - # Passing dtype=np.int64 since randomly generated indices are + # Passing dtype=np.int64 since randomly generated indices are # very large that exceeds int32 limits. idx = mx.nd.random.randint(0, LARGE_X, 10, dtype=np.int64) # Calls gather_nd internally @@ -1063,7 +1062,3 @@ def check_minimum(): check_maximum() check_minimum() - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/nightly/test_np_random.py b/tests/nightly/test_np_random.py index 09ebdad90bd2..0f7ca9c7d681 100644 --- a/tests/nightly/test_np_random.py +++ b/tests/nightly/test_np_random.py @@ -31,8 +31,8 @@ import mxnet as mx from mxnet import np, npx, autograd from mxnet.gluon import HybridBlock -from mxnet.test_utils import same, assert_almost_equal, rand_shape_nd, rand_ndarray, retry, use_np -from common import with_seed +from mxnet.test_utils import same, assert_almost_equal, rand_shape_nd, rand_ndarray, use_np +from common import with_seed, retry from mxnet.test_utils import verify_generator, gen_buckets_probs_with_ppf, assert_exception, is_op_runnable, collapse_sum_like from mxnet.ndarray.ndarray import py_slice from mxnet.base import integer_types @@ -173,7 +173,3 @@ def test_np_laplace(): generator_mx_np = lambda x: np.random.laplace(loc, scale, size=x, ctx=ctx, dtype=dtype).asnumpy() verify_generator(generator=generator_mx_np, buckets=buckets, probs=probs, nsamples=samples, nrepeat=trials) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/nightly/test_optimizer.py b/tests/nightly/test_optimizer.py index c4e264b79b65..0a87368d991e 100644 --- a/tests/nightly/test_optimizer.py +++ b/tests/nightly/test_optimizer.py @@ -88,6 +88,3 @@ def test_lars(): accuracy = acc.get()[1] assert accuracy > 0.98, "LeNet-5 training accuracy on MNIST was too low" -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_contrib_amp.py b/tests/python/gpu/test_contrib_amp.py index 527f8534969c..b7aeeb7ccf37 100644 --- a/tests/python/gpu/test_contrib_amp.py +++ b/tests/python/gpu/test_contrib_amp.py @@ -24,19 +24,27 @@ import collections import ctypes import mxnet.contrib.amp as amp -from nose.tools import assert_raises +import pytest from mxnet.test_utils import set_default_context, download_model, same_symbol_structure from mxnet.gluon.model_zoo.vision import get_model from mxnet.gluon import SymbolBlock, nn, rnn from mxnet.contrib.amp import amp curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import with_seed, teardown, assert_raises_cudnn_not_satisfied +from common import with_seed, teardown_module, assert_raises_cudnn_not_satisfied sys.path.insert(0, os.path.join(curr_path, '../train')) from test_bucketing import train_model set_default_context(mx.gpu(0)) -def test_amp_coverage(): +@pytest.fixture() +def amp_tests(request): + def teardown(): + mx.nd.waitall() + + request.addfinalizer(teardown) + +@pytest.mark.skip(reason='Error during waitall(). Tracked in #18099') +def test_amp_coverage(amp_tests): conditional = [item[0] for item in amp.lists.symbol_fp16.CONDITIONAL_FP32_FUNCS] # Check for duplicates @@ -96,8 +104,9 @@ def test_amp_coverage(): - If you are not sure which list to choose, FP32_FUNCS is the safest option""") +@pytest.mark.skip(reason='Error during waitall(). Tracked in #18099') @with_seed() -def test_amp_conversion(): +def test_amp_conversion(amp_tests): def check_amp_convert_symbol(): x = mx.sym.var("x") y = mx.sym.var("y") @@ -119,18 +128,18 @@ def check_amp_convert_symbol(): "convert_symbol generating wrong computation graph" # convert_symbol called with incorrect inputs - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="float16", target_dtype_ops=["FullyConnected"], fp32_ops=["elemwise_add"]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="float16", target_dtype_ops=["FullyConnected"], fp32_ops=["Activation"], conditional_fp32_ops=[('Activation', 'act_type', ['selu'])]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="float16", target_dtype_ops=["Activation"], fp32_ops=["Activation"], conditional_fp32_ops=[('Activation', 'act_type', ['selu'])]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="float16", target_dtype_ops=["FullyConnected"], fp32_ops=["FullyConnected"]) @@ -345,8 +354,9 @@ def check_amp_convert_bucketing_module(): check_amp_convert_bucketing_module() @with_seed() +@pytest.mark.skip(reason='Error during waitall(). Tracked in #18099') @assert_raises_cudnn_not_satisfied(min_version='5.1.10') -def test_amp_conversion_rnn(): +def test_amp_conversion_rnn(amp_tests): with mx.Context(mx.gpu(0)): model = nn.HybridSequential() model.add(rnn.LSTM(hidden_size=10, num_layers=2, bidirectional=True)) @@ -360,7 +370,8 @@ def test_amp_conversion_rnn(): @with_seed() -def test_module_backward_compatibility(): +@pytest.mark.skip(reason='Error during waitall(). Tracked in #18099') +def test_module_backward_compatibility(amp_tests): channel_num = 10 conv_layer_filter_dims = [2, 3] conv_layer_strides = [1, 1] @@ -403,7 +414,8 @@ def test_module_backward_compatibility(): @with_seed() -def test_fp16_casting(): +@pytest.mark.skip(reason='Error during waitall(). Tracked in #18099') +def test_fp16_casting(amp_tests): data = mx.sym.var("data") out1 = mx.sym.amp_cast(data, dtype="float16") out2 = mx.sym.amp_cast(data, dtype="float32") @@ -484,7 +496,3 @@ def test_fp16_casting(): out = mx.sym.split(concat_res, axis=1, num_outputs=2) final_res = amp.convert_symbol(out) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_deferred_compute_gpu.py b/tests/python/gpu/test_deferred_compute_gpu.py index 7503c7ba102e..9802d2b57d24 100644 --- a/tests/python/gpu/test_deferred_compute_gpu.py +++ b/tests/python/gpu/test_deferred_compute_gpu.py @@ -24,10 +24,6 @@ curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) # We import all tests from ../unittest/test_deferred_compute.py -# They will be detected by nose, as long as the current file has a different filename +# They will be detected by test framework, as long as the current file has a different filename from test_deferred_compute import * - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_forward.py b/tests/python/gpu/test_forward.py index 02b0256024d3..2ec5ee262e0c 100644 --- a/tests/python/gpu/test_forward.py +++ b/tests/python/gpu/test_forward.py @@ -22,7 +22,7 @@ from mxnet.test_utils import * curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.gluon import utils import tarfile diff --git a/tests/python/gpu/test_fusion.py b/tests/python/gpu/test_fusion.py index a6be6c7d6629..eb39fb1777ea 100644 --- a/tests/python/gpu/test_fusion.py +++ b/tests/python/gpu/test_fusion.py @@ -337,6 +337,3 @@ def test_fusion_reshape_executor(): out = f.forward(is_train=False, data1=data, data2=data) assert out[0].sum().asscalar() == 150 -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_gluon_contrib_gpu.py b/tests/python/gpu/test_gluon_contrib_gpu.py index 348e9f77acc8..9b43c797a252 100644 --- a/tests/python/gpu/test_gluon_contrib_gpu.py +++ b/tests/python/gpu/test_gluon_contrib_gpu.py @@ -85,6 +85,3 @@ def test_ModulatedDeformableConvolution(): y = net(x) y.backward() -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_gluon_gpu.py b/tests/python/gpu/test_gluon_gpu.py index 7e90854d923f..b379614a9872 100644 --- a/tests/python/gpu/test_gluon_gpu.py +++ b/tests/python/gpu/test_gluon_gpu.py @@ -27,10 +27,11 @@ import numpy as np import math from mxnet import autograd +import pytest curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown, assert_raises_cudnn_not_satisfied, run_in_spawned_process +from common import setup_module, with_seed, teardown_module, assert_raises_cudnn_not_satisfied, run_in_spawned_process from test_gluon import * from test_loss import * from test_gluon_rnn import * @@ -597,7 +598,7 @@ def hybrid_forward(self, F, a, b): return a + b foo_hybrid = FooHybrid() foo_hybrid.hybridize() - assert_raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,), ctx=mx.gpu()), + pytest.raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,), ctx=mx.gpu()), mx.nd.ones((10,), ctx=mx.cpu()))) @with_seed() @@ -639,7 +640,3 @@ def test_gemms_true_fp16(): atol=atol, rtol=rtol) os.environ["MXNET_FC_TRUE_FP16"] = "0" - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_gluon_model_zoo_gpu.py b/tests/python/gpu/test_gluon_model_zoo_gpu.py index 6f559db62808..6cb5bcf3a1dc 100644 --- a/tests/python/gpu/test_gluon_model_zoo_gpu.py +++ b/tests/python/gpu/test_gluon_model_zoo_gpu.py @@ -25,9 +25,10 @@ import sys import os import unittest +import pytest curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module def eprint(*args, **kwargs): print(*args, file=sys.stderr, **kwargs) @@ -38,60 +39,57 @@ def download_data(): 'http://data.mxnet.io/data/val-5k-256.rec', VAL_DATA) @with_seed() -def test_inference(): - all_models = ['resnet50_v1', 'vgg19_bn', 'alexnet', #'inceptionv3', - 'densenet201', 'squeezenet1.0', 'mobilenet0.25'] - +@pytest.mark.parametrize('model_name', ['resnet50_v1', 'vgg19_bn', 'alexnet', 'densenet201', 'squeezenet1.0', 'mobilenet0.25']) +def test_inference(model_name): batch_size = 10 download_data() - for model_name in all_models: - eprint('testing inference on %s'%model_name) - - data_shape = (3, 224, 224) if 'inception' not in model_name else (3, 299, 299) - dataIter = mx.io.ImageRecordIter( - path_imgrec = VAL_DATA, - label_width = 1, - preprocess_threads = 1, - batch_size = batch_size, - data_shape = data_shape, - label_name = 'softmax_label', - rand_crop = False, - rand_mirror = False) - data_batch = dataIter.next() - data = data_batch.data[0] - label = data_batch.label[0] - gpu_data = data.as_in_context(mx.gpu()) - gpu_label = label.as_in_context(mx.gpu()) - - # This is to create a model and run the model once to initialize - # all parameters. - cpu_model = get_model(model_name) - cpu_model.collect_params().initialize(ctx=mx.cpu()) - cpu_model(mx.nd.array(data, ctx=mx.cpu())) - gpu_model = get_model(model_name) - gpu_model.collect_params().initialize(ctx=mx.gpu()) - gpu_model(mx.nd.array(data, ctx=mx.gpu())) + eprint('testing inference on %s'%model_name) - # Force the two models have the same parameters. - cpu_params = cpu_model.collect_params() - gpu_params = gpu_model.collect_params() - for k in cpu_params.keys(): - k = k.replace(cpu_params.prefix, '') - cpu_param = cpu_params.get(k) - gpu_param = gpu_params.get(k) - gpu_param.set_data(cpu_param.data().as_in_context(mx.gpu())) + data_shape = (3, 224, 224) if 'inception' not in model_name else (3, 299, 299) + dataIter = mx.io.ImageRecordIter( + path_imgrec = VAL_DATA, + label_width = 1, + preprocess_threads = 1, + batch_size = batch_size, + data_shape = data_shape, + label_name = 'softmax_label', + rand_crop = False, + rand_mirror = False) + data_batch = dataIter.next() + data = data_batch.data[0] + label = data_batch.label[0] + gpu_data = data.as_in_context(mx.gpu()) + gpu_label = label.as_in_context(mx.gpu()) - cpu_data = mx.nd.array(data, ctx=mx.cpu()) - for i in range(5): - # Run inference. - with autograd.record(train_mode=False): - cpu_out = cpu_model(cpu_data) - gpu_out = gpu_model(gpu_data) + # This is to create a model and run the model once to initialize + # all parameters. + cpu_model = get_model(model_name) + cpu_model.collect_params().initialize(ctx=mx.cpu()) + cpu_model(mx.nd.array(data, ctx=mx.cpu())) + gpu_model = get_model(model_name) + gpu_model.collect_params().initialize(ctx=mx.gpu()) + gpu_model(mx.nd.array(data, ctx=mx.gpu())) + + # Force the two models have the same parameters. + cpu_params = cpu_model.collect_params() + gpu_params = gpu_model.collect_params() + for k in cpu_params.keys(): + k = k.replace(cpu_params.prefix, '') + cpu_param = cpu_params.get(k) + gpu_param = gpu_params.get(k) + gpu_param.set_data(cpu_param.data().as_in_context(mx.gpu())) + + cpu_data = mx.nd.array(data, ctx=mx.cpu()) + for i in range(5): + # Run inference. + with autograd.record(train_mode=False): + cpu_out = cpu_model(cpu_data) + gpu_out = gpu_model(gpu_data) - max_val = np.max(np.abs(cpu_out.asnumpy())) - gpu_max_val = np.max(np.abs(gpu_out.asnumpy())) - eprint(model_name + ": CPU " + str(max_val) + ", GPU " + str(gpu_max_val)) - assert_almost_equal(cpu_out / max_val, gpu_out / gpu_max_val, rtol=1e-3, atol=1e-3) + max_val = np.max(np.abs(cpu_out.asnumpy())) + gpu_max_val = np.max(np.abs(gpu_out.asnumpy())) + eprint(model_name + ": CPU " + str(max_val) + ", GPU " + str(gpu_max_val)) + assert_almost_equal(cpu_out / max_val, gpu_out / gpu_max_val, rtol=1e-3, atol=1e-3) def get_nn_model(name): if "densenet" in name: @@ -180,6 +178,3 @@ def test_training(): gpu_param = gpu_params.get(k) assert_almost_equal(cpu_param.data(), gpu_param.data(), rtol=1e-3, atol=1e-3) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_gluon_transforms.py b/tests/python/gpu/test_gluon_transforms.py index e777f0bb90e2..23addbffc20f 100644 --- a/tests/python/gpu/test_gluon_transforms.py +++ b/tests/python/gpu/test_gluon_transforms.py @@ -27,7 +27,7 @@ from mxnet.test_utils import almost_equal, same curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import assertRaises, setup_module, with_seed, teardown +from common import assertRaises, setup_module, with_seed, teardown_module from test_gluon_data_vision import test_to_tensor, test_normalize, test_crop_resize set_default_context(mx.gpu(0)) diff --git a/tests/python/gpu/test_kvstore_gpu.py b/tests/python/gpu/test_kvstore_gpu.py index a986f70d7525..f83220ad2e61 100644 --- a/tests/python/gpu/test_kvstore_gpu.py +++ b/tests/python/gpu/test_kvstore_gpu.py @@ -24,7 +24,7 @@ from mxnet.test_utils import assert_almost_equal, default_context, EnvManager curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module shape = (4, 4) keys = [5, 7, 11] @@ -40,12 +40,12 @@ def init_kv_with_str(stype='default', kv_type='local'): return kv # 1. Test seed 89411477 (module seed 1829754103) resulted in a py3-gpu CI runner core dump. -# 2. Test seed 1155716252 (module seed 1032824746) resulted in py3-mkldnn-gpu have error +# 2. Test seed 1155716252 (module seed 1032824746) resulted in py3-mkldnn-gpu have error # src/operator/nn/mkldnn/mkldnn_base.cc:567: Check failed: similar # Both of them are not reproducible, so this test is back on random seeds. @with_seed() @unittest.skipIf(mx.context.num_gpus() < 2, "test_rsp_push_pull needs more than 1 GPU") -@unittest.skip("Flaky test https://github.com/apache/incubator-mxnet/issues/14189") +@unittest.skip("Flaky test https://github.com/apache/incubator-mxnet/issues/14189") def test_rsp_push_pull(): def check_rsp_push_pull(kv_type, sparse_pull, is_push_cpu=True): kv = init_kv_with_str('row_sparse', kv_type) @@ -134,6 +134,3 @@ def test_rsp_push_pull_large_rowid(): kv.row_sparse_pull('a', out=out, row_ids=mx.nd.arange(0, num_rows, dtype='int64')) assert(out.indices.shape[0] == num_rows) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_numpy_fallback.py b/tests/python/gpu/test_numpy_fallback.py index 1499e1b15c57..71ca09c5ab2e 100644 --- a/tests/python/gpu/test_numpy_fallback.py +++ b/tests/python/gpu/test_numpy_fallback.py @@ -26,7 +26,6 @@ import mxnet as mx import scipy.stats as ss import scipy.special as scipy_special -from nose.tools import assert_raises from mxnet import np, npx from mxnet.base import MXNetError from mxnet.test_utils import assert_almost_equal, use_np, set_default_context @@ -109,7 +108,3 @@ def empty_ret_func(): # does not support functions with no return values assertRaises(ValueError, empty_ret_func) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_operator_gpu.py b/tests/python/gpu/test_operator_gpu.py index a017b8ce59c2..798f861f1695 100644 --- a/tests/python/gpu/test_operator_gpu.py +++ b/tests/python/gpu/test_operator_gpu.py @@ -23,14 +23,14 @@ import mxnet as mx import numpy as np import unittest -from nose.tools import assert_raises +import pytest from mxnet.test_utils import check_consistency, set_default_context, assert_almost_equal, assert_allclose from mxnet.base import MXNetError from mxnet import autograd curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown, assert_raises_cudnn_not_satisfied, assert_raises_cuda_not_satisfied +from common import setup_module, with_seed, teardown_module, assert_raises_cudnn_not_satisfied, assert_raises_cuda_not_satisfied from common import run_in_spawned_process from test_operator import * from test_numpy_ndarray import * @@ -46,7 +46,6 @@ from test_subgraph_op import * from test_gluon_gpu import _test_bulking from test_contrib_operator import test_multibox_target_op -from test_tvm_op import * from test_contrib_optimizer import test_adamw set_default_context(mx.gpu(0)) @@ -1342,7 +1341,7 @@ def test_bilinear_resize_op(): check_consistency(sym, ctx_list) sym = mx.sym.contrib.BilinearResize2D(data, height=10, width=5, align_corners=False) - check_consistency(sym, ctx_list) + check_consistency(sym, ctx_list) sym = mx.sym.contrib.BilinearResize2D(data, None, scale_height=2, scale_width=0.5, mode='odd_scale', align_corners=True) check_consistency(sym, ctx_list) @@ -2274,7 +2273,7 @@ def test_kernel_error_checking(): def test_incorrect_gpu(): # Try setting dev_id to a really big number - assert_raises(MXNetError, mx.nd.ones, (2,2), ctx=mx.gpu(100001)) + pytest.raises(MXNetError, mx.nd.ones, (2,2), ctx=mx.gpu(100001)) @with_seed() def test_batchnorm_backwards_notrain(): @@ -2526,7 +2525,7 @@ def run_math(op, shape, dtype="float32", check_value=True): def test_math(): ops = ['log', 'erf', 'square'] check_value= True - shape_lst = [[1000], [100,1000], [10,100,100], [10,100,100,100]] + shape_lst = [[1000], [100,1000], [10,100,100], [10,100,100,100]] dtypes = ["float32", "float64"] for shape in shape_lst: for dtype in dtypes: @@ -2548,6 +2547,3 @@ def test_arange_like_dtype(): for v in out: assert v.dtype == t -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_predictor.py b/tests/python/gpu/test_predictor.py index 4838a76c7cb1..592733a90174 100644 --- a/tests/python/gpu/test_predictor.py +++ b/tests/python/gpu/test_predictor.py @@ -31,7 +31,7 @@ from mxnet.contrib.amp import amp from mxnet.base import NDArrayHandle, py_str sys.path.insert(0, os.path.join(curr_path, '../unittest')) -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module @with_seed() def test_predictor_with_dtype(): @@ -122,7 +122,3 @@ def test_predictor_amp(): cast_optional_params=True) compare_module_cpredict(result_sym, result_arg_params, result_aux_params, monitor_callback=True) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_tvm_bridge.py b/tests/python/gpu/test_tvm_bridge.py index 5c87536bdbae..7a4339c6ae94 100644 --- a/tests/python/gpu/test_tvm_bridge.py +++ b/tests/python/gpu/test_tvm_bridge.py @@ -61,7 +61,3 @@ def check(target, dtype): "float32", "float64"]: check(tgt, dtype) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/gpu/test_tvm_op_gpu.py b/tests/python/gpu/test_tvm_op_gpu.py new file mode 100644 index 000000000000..fbb16bf9d1a9 --- /dev/null +++ b/tests/python/gpu/test_tvm_op_gpu.py @@ -0,0 +1,27 @@ +# Licensed to the Apache Software Foundation (ASF) under one +# or more contributor license agreements. See the NOTICE file +# distributed with this work for additional information +# regarding copyright ownership. The ASF licenses this file +# to you under the Apache License, Version 2.0 (the +# "License"); you may not use this file except in compliance +# with the License. You may obtain a copy of the License at +# +# http://www.apache.org/licenses/LICENSE-2.0 +# +# Unless required by applicable law or agreed to in writing, +# software distributed under the License is distributed on an +# "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY +# KIND, either express or implied. See the License for the +# specific language governing permissions and limitations +# under the License. + +import mxnet as mx +from mxnet.test_utils import set_default_context +import os +import sys +curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) +sys.path.insert(0, os.path.join(curr_path, '../unittest')) +from common import setup_module, teardown_module +from test_tvm_op import * + +set_default_context(mx.gpu(0)) diff --git a/tests/python/mkl/test_bf16_operator.py b/tests/python/mkl/test_bf16_operator.py index b275c96bbb67..888b5d20b908 100644 --- a/tests/python/mkl/test_bf16_operator.py +++ b/tests/python/mkl/test_bf16_operator.py @@ -25,7 +25,6 @@ import ctypes import itertools import mxnet.contrib.amp as amp -from nose.tools import assert_raises from mxnet.test_utils import set_default_context, download_model, same_symbol_structure, assert_almost_equal_with_err, rand_shape_nd from mxnet.gluon.model_zoo.vision import get_model from mxnet.gluon import SymbolBlock, nn, rnn @@ -55,7 +54,7 @@ def check_operator_accuracy(sym_fp32, sym_bf16, data_shape, num_input_data=1, bf the relative threshold atol: float the absolute threshold - etol: float + etol: float The error rate threshold, allow a small amount of value not consistent between bf16 and fp32 """ if not isinstance(data_shape, tuple): @@ -105,7 +104,7 @@ def check_operator_accuracy(sym_fp32, sym_bf16, data_shape, num_input_data=1, bf exe_bf16.arg_dict[arg_name][:] = arg_params_fp32[arg_name] else: exe_bf16.arg_dict[arg_name][:] = mx.nd.amp_cast(arg_params_fp32[arg_name], dtype=bfloat16) - + for aux_name in aux_names: if bf16_use_fp32_params: exe_bf16.aux_dict[aux_name][:] = aux_params_fp32[aux_name] @@ -169,7 +168,7 @@ def test_bf16_pooling(): pool_conventions = ["full", "valid"] for new_params in itertools.product(data_shapes, pool_types, pool_conventions): pool_params.update({"pool_type": new_params[1], "pooling_convention": new_params[2]}) - + data_sym_fp32 = mx.sym.Variable(name='data') data_sym_bf16 = mx.sym.Variable(name='data', dtype=bfloat16) pool_fp32 = mx.sym.Pooling(data_sym_fp32, **pool_params) @@ -230,7 +229,7 @@ def test_bf16_abs(): data_sym_bf16 = mx.sym.Variable(name='data', dtype=bfloat16) sym_fp32 = mx.sym.abs(data_sym_fp32) sym_bf16 = mx.sym.abs(data_sym_bf16) - + check_operator_accuracy(sym_fp32, sym_bf16, data_shape, bf16_use_fp32_params=True) @with_seed() @@ -285,6 +284,3 @@ def test_bf16_fallback(): conv_bf16 = mx.sym.Convolution(data_sym_bf16, **conv_params) check_operator_accuracy(sym_fp32=conv_fp32, sym_bf16=conv_bf16, data_shape=(3, 32, 28, 28, 4), bf16_use_fp32_params=False) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/mkl/test_contrib_amp.py b/tests/python/mkl/test_contrib_amp.py index 5d5774099255..ec88851751ff 100644 --- a/tests/python/mkl/test_contrib_amp.py +++ b/tests/python/mkl/test_contrib_amp.py @@ -24,7 +24,7 @@ import collections import ctypes import mxnet.contrib.amp as amp -from nose.tools import assert_raises +import pytest from mxnet.test_utils import set_default_context, download_model, same_symbol_structure, assert_almost_equal from mxnet.gluon.model_zoo.vision import get_model from mxnet.gluon import SymbolBlock, nn, rnn @@ -117,18 +117,18 @@ def check_amp_convert_symbol(): "convert_symbol generating wrong computation graph" # convert_symbol called with incorrect inputs - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="bfloat16", target_dtype_ops=["FullyConnected"], fp32_ops=["elemwise_add"]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="bfloat16", target_dtype_ops=["FullyConnected"], fp32_ops=["Activation"], conditional_fp32_ops=[('Activation', 'act_type', ['selu'])]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="bfloat16", target_dtype_ops=["Activation"], fp32_ops=["Activation"], conditional_fp32_ops=[('Activation', 'act_type', ['selu'])]) - assert_raises(AssertionError, amp.convert_symbol, res, + pytest.raises(AssertionError, amp.convert_symbol, res, target_dtype="bfloat16", target_dtype_ops=["FullyConnected"], fp32_ops=["FullyConnected"]) @@ -495,7 +495,3 @@ def test_bf16_casting(): exe = final_res.simple_bind(ctx=mx.cpu(), data=(1, 2), data2=(1, 2)) assert exe.arg_arrays[0].dtype == bfloat16 - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/mkl/test_mkldnn.py b/tests/python/mkl/test_mkldnn.py index 731a761dd1d8..82519a11d919 100644 --- a/tests/python/mkl/test_mkldnn.py +++ b/tests/python/mkl/test_mkldnn.py @@ -702,6 +702,3 @@ def check_elemwise_add_training(stype): for stype in stypes: check_elemwise_add_training(stype) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/mkl/test_quantization_mkldnn.py b/tests/python/mkl/test_quantization_mkldnn.py index 8ba2f2b01feb..f2432175720a 100644 --- a/tests/python/mkl/test_quantization_mkldnn.py +++ b/tests/python/mkl/test_quantization_mkldnn.py @@ -25,7 +25,7 @@ from test_quantization import * if __name__ == '__main__': - import nose - nose.runmodule() + import pytest + pytest.main() del os.environ['ENABLE_MKLDNN_QUANTIZATION_TEST'] del os.environ['MXNET_SUBGRAPH_BACKEND'] diff --git a/tests/python/mkl/test_subgraph.py b/tests/python/mkl/test_subgraph.py index 65b73e438ea6..862fd9078c69 100644 --- a/tests/python/mkl/test_subgraph.py +++ b/tests/python/mkl/test_subgraph.py @@ -999,7 +999,3 @@ def test_quantized_fc_bias_overflow(): helper_quantized_fc_bias_overflow(-1e-6, +1e-6, -1e-6, +1e-6) helper_quantized_fc_bias_overflow(0, 0, 0, 0) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/profiling/test_nvtx.py b/tests/python/profiling/test_nvtx.py index 507b438e300d..a80e33ec03b0 100644 --- a/tests/python/profiling/test_nvtx.py +++ b/tests/python/profiling/test_nvtx.py @@ -46,7 +46,3 @@ def test_nvtx_ranges_present_in_profile(): # Verify that we have some expected output from the engine. assert "Range \"WaitForVar\"" in profiler_output - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/quantization/test_quantization.py b/tests/python/quantization/test_quantization.py index 4e42a5dfcf60..2572cabba9a4 100644 --- a/tests/python/quantization/test_quantization.py +++ b/tests/python/quantization/test_quantization.py @@ -1257,7 +1257,3 @@ def get_threshold(nd): assert 'layer1' in th_dict assert_almost_equal(np.array([th_dict['layer1'][1]]), expected_threshold, rtol=1e-2, atol=1e-4) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/quantization_gpu/test_quantization_gpu.py b/tests/python/quantization_gpu/test_quantization_gpu.py index 4f2d70effd49..0f14fa1ac961 100644 --- a/tests/python/quantization_gpu/test_quantization_gpu.py +++ b/tests/python/quantization_gpu/test_quantization_gpu.py @@ -25,8 +25,3 @@ from test_quantization import * set_default_context(mx.gpu(0)) - - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/tensorrt/lenet5_train.py b/tests/python/tensorrt/lenet5_train.py old mode 100755 new mode 100644 diff --git a/tests/python/tensorrt/test_cvnets.py b/tests/python/tensorrt/test_cvnets.py index 4b8eb48e926c..99312d76dc7a 100644 --- a/tests/python/tensorrt/test_cvnets.py +++ b/tests/python/tensorrt/test_cvnets.py @@ -167,8 +167,3 @@ def test_tensorrt_on_cifar_resnets(batch_size=32, tolerance=0.1, num_workers=1): finally: mx.contrib.tensorrt.set_use_fp16(original_use_fp16) - -if __name__ == '__main__': - import nose - - nose.runmodule() diff --git a/tests/python/tensorrt/test_ops.py b/tests/python/tensorrt/test_ops.py index af1c453111d9..dfbbb8e8883c 100644 --- a/tests/python/tensorrt/test_ops.py +++ b/tests/python/tensorrt/test_ops.py @@ -512,6 +512,3 @@ def test_dropout(): sym = mx.sym.Dropout(data, p=0.7, mode=mode, axes=(0,)) check_unsupported_single_sym(sym) -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/tensorrt/test_resnet18.py b/tests/python/tensorrt/test_resnet18.py index 9fd99abb121b..e146423e257d 100644 --- a/tests/python/tensorrt/test_resnet18.py +++ b/tests/python/tensorrt/test_resnet18.py @@ -69,6 +69,3 @@ def test_tensorrt_resnet18_feature_vect(): finally: mx.contrib.tensorrt.set_use_fp16(original_precision_value) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/tensorrt/test_tensorrt_lenet5.py b/tests/python/tensorrt/test_tensorrt_lenet5.py index 78f41ca53909..a34b634121d2 100644 --- a/tests/python/tensorrt/test_tensorrt_lenet5.py +++ b/tests/python/tensorrt/test_tensorrt_lenet5.py @@ -116,6 +116,3 @@ def test_tensorrt_inference(): """Absolute diff. between MXNet & TensorRT accuracy (%f) exceeds threshold (%f): MXNet = %f, TensorRT = %f""" % (absolute_accuracy_diff, epsilon, mx_pct, trt_pct) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/train/test_conv.py b/tests/python/train/test_conv.py old mode 100644 new mode 100755 diff --git a/tests/python/unittest/common.py b/tests/python/unittest/common.py index ab2d191f1360..eac0265fb747 100644 --- a/tests/python/unittest/common.py +++ b/tests/python/unittest/common.py @@ -16,7 +16,7 @@ # under the License. from __future__ import print_function -import sys, os, logging +import sys, os, logging, functools import multiprocessing as mp import mxnet as mx import numpy as np @@ -29,7 +29,7 @@ import models from contextlib import contextmanager -from nose.tools import make_decorator, assert_raises +import pytest import tempfile def assertRaises(expected_exception, func, *args, **kwargs): @@ -43,7 +43,7 @@ def assertRaises(expected_exception, func, *args, **kwargs): def default_logger(): - """A logger used to output seed information to nosetests logs.""" + """A logger used to output seed information to logs.""" logger = logging.getLogger(__name__) # getLogger() lookups will return the same logger, but only add the handler once. if not len(logger.handlers): @@ -109,7 +109,7 @@ def less_than(version_left, version_right): left = version_left.split(".") right = version_right.split(".") - # 0 pad shortest version - e.g. + # 0 pad shortest version - e.g. # less_than("9.1", "9.1.9") == less_than("9.1.0", "9.1.9") longest = max(len(left), len(right)) left.extend([0] * (longest - len(left))) @@ -123,7 +123,7 @@ def less_than(version_left, version_right): return False def test_helper(orig_test): - @make_decorator(orig_test) + @functools.wraps(orig_test) def test_new(*args, **kwargs): cuxx_off = os.getenv(cfg['TEST_OFF_ENV_VAR']) == 'true' cuxx_env_version = os.getenv(cfg['VERSION_ENV_VAR'], None if cuxx_off else cfg['DEFAULT_VERSION']) @@ -131,7 +131,7 @@ def test_new(*args, **kwargs): if not cuxx_test_disabled or mx.context.current_context().device_type == 'cpu': orig_test(*args, **kwargs) else: - assert_raises((MXNetError, RuntimeError), orig_test, *args, **kwargs) + pytest.raises((MXNetError, RuntimeError), orig_test, *args, **kwargs) return test_new return test_helper @@ -154,7 +154,7 @@ def assert_raises_cuda_not_satisfied(min_version): def with_seed(seed=None): """ - A decorator for nosetests test functions that manages rng seeds. + A decorator for test functions that manages rng seeds. Parameters ---------- @@ -181,13 +181,13 @@ def test_not_ok_with_random_data(): can then set the environment variable MXNET_TEST_SEED to the value reported, then rerun the test with: - nosetests --verbose -s : + pytest --verbose --capture=no :: To run a test repeatedly, set MXNET_TEST_COUNT= in the environment. - To see the seeds of even the passing tests, add '--logging-level=DEBUG' to nosetests. + To see the seeds of even the passing tests, add '--log-level=DEBUG' to pytest. """ def test_helper(orig_test): - @make_decorator(orig_test) + @functools.wraps(orig_test) def test_new(*args, **kwargs): test_count = int(os.getenv('MXNET_TEST_COUNT', '1')) env_seed_str = os.getenv('MXNET_TEST_SEED') @@ -206,7 +206,7 @@ def test_new(*args, **kwargs): mx.random.seed(this_test_seed) random.seed(this_test_seed) logger = default_logger() - # 'nosetests --logging-level=DEBUG' shows this msg even with an ensuing core dump. + # 'pytest --logging-level=DEBUG' shows this msg even with an ensuing core dump. test_count_msg = '{} of {}: '.format(i+1,test_count) if test_count > 1 else '' test_msg = ('{}Setting test np/mx/python random seeds, use MXNET_TEST_SEED={}' ' to reproduce.').format(test_count_msg, this_test_seed) @@ -226,12 +226,12 @@ def test_new(*args, **kwargs): def setup_module(): """ - A function with a 'magic name' executed automatically before each nosetests module + A function with a 'magic name' executed automatically before each pytest module (file of tests) that helps reproduce a test segfault by setting and outputting the rng seeds. The segfault-debug procedure on a module called test_module.py is: - 1. run "nosetests --verbose test_module.py". A seg-faulting output might be: + 1. run "pytest --verbose test_module.py". A seg-faulting output might be: [INFO] np, mx and python random seeds = 4018804151 test_module.test1 ... ok @@ -239,7 +239,7 @@ def setup_module(): 2. Copy the module-starting seed into the next command, then run: - MXNET_MODULE_SEED=4018804151 nosetests --logging-level=DEBUG --verbose test_module.py + MXNET_MODULE_SEED=4018804151 pytest --logging-level=DEBUG --verbose test_module.py Output might be: @@ -251,7 +251,7 @@ def setup_module(): Illegal instruction (core dumped) 3. Copy the segfaulting-test seed into the command: - MXNET_TEST_SEED=1435005594 nosetests --logging-level=DEBUG --verbose test_module.py:test2 + MXNET_TEST_SEED=1435005594 pytest --logging-level=DEBUG --verbose test_module.py:test2 Output might be: [INFO] np, mx and python random seeds = 2481884723 @@ -301,9 +301,9 @@ def __enter__(self): def __exit__(self, exc_type, exc_value, traceback): shutil.rmtree(self._dirname) -def teardown(): +def teardown_module(): """ - A function with a 'magic name' executed automatically after each nosetests test module. + A function with a 'magic name' executed automatically after each pytest test module. It waits for all operations in one file to finish before carrying on the next. """ @@ -316,7 +316,7 @@ def with_post_test_cleanup(): Required especially by large tensor tests that have memory footprints in GBs. """ def test_helper(orig_test): - @make_decorator(orig_test) + @functools.wraps(orig_test) def test_new(*args, **kwargs): logger = default_logger() try: @@ -373,4 +373,25 @@ def run_in_spawned_process(func, env, *args): finally: os.environ.clear() os.environ.update(orig_environ) - return True \ No newline at end of file + return True + + +def retry(n): + """Retry n times before failing for stochastic test cases.""" + # TODO(szha): replace with flaky + # https://github.com/apache/incubator-mxnet/issues/17803 + assert n > 0 + def test_helper(orig_test): + @functools.wraps(orig_test) + def test_new(*args, **kwargs): + """Wrapper for tests function.""" + for _ in range(n): + try: + orig_test(*args, **kwargs) + except AssertionError as e: + err = e + continue + return + raise err + return test_new + return test_helper diff --git a/tests/python-pytest/onnx/README.md b/tests/python/unittest/onnx/README.md similarity index 100% rename from tests/python-pytest/onnx/README.md rename to tests/python/unittest/onnx/README.md diff --git a/tests/python-pytest/onnx/backend.py b/tests/python/unittest/onnx/backend.py similarity index 100% rename from tests/python-pytest/onnx/backend.py rename to tests/python/unittest/onnx/backend.py diff --git a/tests/python-pytest/onnx/backend_rep.py b/tests/python/unittest/onnx/backend_rep.py similarity index 100% rename from tests/python-pytest/onnx/backend_rep.py rename to tests/python/unittest/onnx/backend_rep.py diff --git a/tests/python-pytest/onnx/backend_test.py b/tests/python/unittest/onnx/backend_test.py old mode 100755 new mode 100644 similarity index 95% rename from tests/python-pytest/onnx/backend_test.py rename to tests/python/unittest/onnx/backend_test.py index 5e8e1983c729..69d9e1427b69 --- a/tests/python-pytest/onnx/backend_test.py +++ b/tests/python/unittest/onnx/backend_test.py @@ -35,7 +35,7 @@ pytest_plugins = "onnx.backend.test.report", -def test_suite(backend_tests): # type: () -> unittest.TestSuite +def build_test_suite(backend_tests): # type: () -> unittest.TestSuite ''' TestSuite that can be run by TestRunner This has been borrowed from onnx/onnx/backend/test/runner/__init__.py, @@ -89,4 +89,4 @@ def prepare_tests(backend, oper): log.info('Executing tests for ' + bkend + ' backend: ' + operation) mxnet_backend.MXNetBackend.set_params(bkend, operation) BACKEND_TESTS = prepare_tests(mxnet_backend, operation) - unittest.TextTestRunner().run(test_suite(BACKEND_TESTS.enable_report())) + unittest.TextTestRunner().run(build_test_suite(BACKEND_TESTS.enable_report())) diff --git a/tests/python-pytest/onnx/mxnet_export_test.py b/tests/python/unittest/onnx/mxnet_export_test.py similarity index 90% rename from tests/python-pytest/onnx/mxnet_export_test.py rename to tests/python/unittest/onnx/mxnet_export_test.py index 90e92cccee06..117a2cf93241 100644 --- a/tests/python-pytest/onnx/mxnet_export_test.py +++ b/tests/python/unittest/onnx/mxnet_export_test.py @@ -18,11 +18,15 @@ # pylint: disable=too-many-locals,wrong-import-position,import-error from __future__ import absolute_import -import os +import os, sys import unittest import logging import tempfile +curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) +sys.path.insert(0, os.path.join(curr_path, '..')) +from common import setup_module, teardown_module, with_seed from mxnet import nd, sym +from mxnet.test_utils import set_default_context from mxnet.gluon import nn from mxnet.contrib import onnx as onnx_mxnet import mxnet as mx @@ -30,7 +34,6 @@ logger = logging.getLogger() logger.setLevel(logging.DEBUG) - def _assert_sym_equal(lhs, rhs): assert lhs.list_inputs() == rhs.list_inputs() # input names must be identical assert len(lhs.list_outputs()) == len(rhs.list_outputs()) # number of outputs must be identical @@ -74,19 +77,24 @@ def _check_onnx_export(net, group_outputs=False, shape_type=tuple, extra_params= # Confirm network outputs are the same imported_net_output = _force_list(imported_net(data)) for out, imp_out in zip(output, imported_net_output): - mx.test_utils.assert_almost_equal(out, imp_out) + mx.test_utils.assert_almost_equal(out, imp_out, atol=1e-5, rtol=1e-5) class TestExport(unittest.TestCase): """ Tests ONNX export. """ + def setUp(self): + set_default_context(mx.cpu(0)) + + @with_seed() def test_onnx_export_single_output(self): net = nn.HybridSequential(prefix='single_output_net') with net.name_scope(): net.add(nn.Dense(100, activation='relu'), nn.Dense(10)) _check_onnx_export(net) + @with_seed() def test_onnx_export_multi_output(self): class MultiOutputBlock(nn.HybridBlock): def __init__(self): @@ -104,18 +112,17 @@ def hybrid_forward(self, F, x): assert len(sym.Group(net(sym.Variable('data'))).list_outputs()) == 10 _check_onnx_export(net, group_outputs=True) + @with_seed() def test_onnx_export_list_shape(self): net = nn.HybridSequential(prefix='list_shape_net') with net.name_scope(): net.add(nn.Dense(100, activation='relu'), nn.Dense(10)) _check_onnx_export(net, shape_type=list) + @with_seed() def test_onnx_export_extra_params(self): net = nn.HybridSequential(prefix='extra_params_net') with net.name_scope(): net.add(nn.Dense(100, activation='relu'), nn.Dense(10)) _check_onnx_export(net, extra_params={'extra_param': nd.array([1, 2])}) - -if __name__ == '__main__': - unittest.main() diff --git a/tests/python-pytest/onnx/test_cases.py b/tests/python/unittest/onnx/test_cases.py similarity index 100% rename from tests/python-pytest/onnx/test_cases.py rename to tests/python/unittest/onnx/test_cases.py diff --git a/tests/python-pytest/onnx/test_models.py b/tests/python/unittest/onnx/test_models.py similarity index 57% rename from tests/python-pytest/onnx/test_models.py rename to tests/python/unittest/onnx/test_models.py index f85786141d6e..ce54a349003e 100644 --- a/tests/python-pytest/onnx/test_models.py +++ b/tests/python/unittest/onnx/test_models.py @@ -20,7 +20,7 @@ from __future__ import absolute_import import sys import os -import unittest +import pytest import logging import tarfile from collections import namedtuple @@ -101,78 +101,64 @@ def forward_pass(sym, arg, aux, data_names, input_data): return mod.get_outputs()[0].asnumpy() -class TestModel(unittest.TestCase): - """ Tests for models. - Tests are dynamically added. - Therefore edit test_models to add more tests. - """ - def test_import_export(self): - def get_model_results(modelpath): - symbol, args, aux = onnx_mxnet.import_model(modelpath) - - data = onnx_mxnet.get_model_metadata(modelpath) - data_names = [input_name[0] for input_name in data.get('input_tensor_data')] - - result = [] - for input_data, output_data in zip(inputs, outputs): - output = forward_pass(symbol, args, aux, data_names, input_data) - result.append(output) - return symbol, args, aux, result, data - - for test in test_cases: - model_name, input_shape, output_shape = test - with self.subTest(model_name): - model_path, inputs, outputs = get_test_files(model_name) - logging.info("Translating " + model_name + " from ONNX model zoo to MXNet") - - sym, arg_params, aux_params, expected_result, _ = get_model_results(model_path) - - params = {} - params.update(arg_params) - params.update(aux_params) - - dir_path = os.path.dirname(model_path) - new_model_name = "exported_" + model_name + ".onnx" - onnx_file = os.path.join(dir_path, new_model_name) - - logging.info("Translating converted model from mxnet to ONNX") - converted_model_path = onnx_mxnet.export_model(sym, params, [input_shape], np.float32, onnx_file) - - sym, arg_params, aux_params, actual_result, metadata = get_model_results(converted_model_path) - - assert len(metadata) == 2 - assert metadata.get('input_tensor_data') - assert metadata.get('input_tensor_data')[0][1] == input_shape - assert metadata.get('output_tensor_data') - assert metadata.get('output_tensor_data')[0][1] == output_shape - - # verify the results - for expected, actual in zip(expected_result, actual_result): - npt.assert_equal(expected.shape, actual.shape) - npt.assert_almost_equal(expected, actual, decimal=3) - - logging.info(model_name + " conversion successful") - - def test_nodims_import(self): - # Download test model without dims mentioned in params - test_model = download(test_model_path, dirname=CURR_PATH.__str__()) - input_data = np.array([0.2, 0.5]) - nd_data = mx.nd.array(input_data).expand_dims(0) - sym, arg_params, aux_params = onnx_mxnet.import_model(test_model) - model_metadata = onnx_mxnet.get_model_metadata(test_model) - input_names = [inputs[0] for inputs in model_metadata.get('input_tensor_data')] - output_data = forward_pass(sym, arg_params, aux_params, input_names, nd_data) - assert(output_data.shape == (1,1)) - -# test_case = ("model name", input shape, output shape) -test_cases = [ +@pytest.mark.parametrize('model_name,input_shape,output_shape', [ ("bvlc_googlenet", (1, 3, 224, 224), (1, 1000)), ("bvlc_reference_caffenet", (1, 3, 224, 224), (1, 1000)), ("bvlc_reference_rcnn_ilsvrc13", (1, 3, 224, 224), (1, 200)), ("inception_v1", (1, 3, 224, 224), (1, 1000)), ("inception_v2", (1, 3, 224, 224), (1, 1000)) -] - - -if __name__ == '__main__': - unittest.main() +]) +def test_import_export(model_name, input_shape, output_shape): + def get_model_results(modelpath): + symbol, args, aux = onnx_mxnet.import_model(modelpath) + + data = onnx_mxnet.get_model_metadata(modelpath) + data_names = [input_name[0] for input_name in data.get('input_tensor_data')] + + result = [] + for input_data, output_data in zip(inputs, outputs): + output = forward_pass(symbol, args, aux, data_names, input_data) + result.append(output) + return symbol, args, aux, result, data + + model_path, inputs, outputs = get_test_files(model_name) + logging.info("Translating " + model_name + " from ONNX model zoo to MXNet") + + sym, arg_params, aux_params, expected_result, _ = get_model_results(model_path) + + params = {} + params.update(arg_params) + params.update(aux_params) + + dir_path = os.path.dirname(model_path) + new_model_name = "exported_" + model_name + ".onnx" + onnx_file = os.path.join(dir_path, new_model_name) + + logging.info("Translating converted model from mxnet to ONNX") + converted_model_path = onnx_mxnet.export_model(sym, params, [input_shape], np.float32, onnx_file) + + sym, arg_params, aux_params, actual_result, metadata = get_model_results(converted_model_path) + + assert len(metadata) == 2 + assert metadata.get('input_tensor_data') + assert metadata.get('input_tensor_data')[0][1] == input_shape + assert metadata.get('output_tensor_data') + assert metadata.get('output_tensor_data')[0][1] == output_shape + + # verify the results + for expected, actual in zip(expected_result, actual_result): + npt.assert_equal(expected.shape, actual.shape) + npt.assert_almost_equal(expected, actual, decimal=3) + + logging.info(model_name + " conversion successful") + +def test_nodims_import(): + # Download test model without dims mentioned in params + test_model = download(test_model_path, dirname=CURR_PATH.__str__()) + input_data = np.array([0.2, 0.5]) + nd_data = mx.nd.array(input_data).expand_dims(0) + sym, arg_params, aux_params = onnx_mxnet.import_model(test_model) + model_metadata = onnx_mxnet.get_model_metadata(test_model) + input_names = [inputs[0] for inputs in model_metadata.get('input_tensor_data')] + output_data = forward_pass(sym, arg_params, aux_params, input_names, nd_data) + assert(output_data.shape == (1,1)) diff --git a/tests/python-pytest/onnx/test_node.py b/tests/python/unittest/onnx/test_node.py similarity index 94% rename from tests/python-pytest/onnx/test_node.py rename to tests/python/unittest/onnx/test_node.py index 96045516c69e..f7fc5c855213 100644 --- a/tests/python-pytest/onnx/test_node.py +++ b/tests/python/unittest/onnx/test_node.py @@ -161,7 +161,7 @@ def test_import_export(self): onnx_attrs = _fix_attributes(attrs, fix_attrs) onnxmodel = get_onnx_graph(test_name, names, input_tensors, onnx_name, outputshape, onnx_attrs) - bkd_rep = backend.prepare(onnxmodel, operation='export') + bkd_rep = backend.prepare(onnxmodel, operation='export', backend='mxnet') output = bkd_rep.run(inputs) if check_value: @@ -195,16 +195,17 @@ def test_import_export(self): npt.assert_almost_equal(result, forward_op) def test_imports(self): - for test in import_test_cases: - test_name, onnx_name, inputs, np_op, attrs = test - with self.subTest(test_name): - names, input_tensors, inputsym = get_input_tensors(inputs) - np_out = [np_op(*inputs, **attrs)] - output_shape = np.shape(np_out) - onnx_model = get_onnx_graph(test_name, names, input_tensors, onnx_name, output_shape, attrs) - bkd_rep = backend.prepare(onnx_model, operation='import') - mxnet_out = bkd_rep.run(inputs) - npt.assert_almost_equal(np_out, mxnet_out, decimal=4) + for bk in ['mxnet', 'gluon']: + for test in import_test_cases: + test_name, onnx_name, inputs, np_op, attrs = test + with self.subTest(test_name): + names, input_tensors, inputsym = get_input_tensors(inputs) + np_out = [np_op(*inputs, **attrs)] + output_shape = np.shape(np_out) + onnx_model = get_onnx_graph(test_name, names, input_tensors, onnx_name, output_shape, attrs) + bkd_rep = backend.prepare(onnx_model, operation='import', backend=bk) + mxnet_out = bkd_rep.run(inputs) + npt.assert_almost_equal(np_out, mxnet_out, decimal=4) def test_exports(self): input_shape = (2,1,3,1) diff --git a/tests/python/unittest/test_autograd.py b/tests/python/unittest/test_autograd.py index 61955f034a71..69b61b47d4c9 100644 --- a/tests/python/unittest/test_autograd.py +++ b/tests/python/unittest/test_autograd.py @@ -20,7 +20,7 @@ from mxnet.ndarray import zeros_like from mxnet.autograd import * from mxnet.test_utils import * -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.test_utils import EnvManager @@ -467,7 +467,3 @@ def test_gradient(): dx.backward() assert abs(x.grad.asscalar() - 2.71828175) < 1e-7 - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_base.py b/tests/python/unittest/test_base.py index 3189729e1d10..07d429589ba2 100644 --- a/tests/python/unittest/test_base.py +++ b/tests/python/unittest/test_base.py @@ -17,7 +17,6 @@ import mxnet as mx from mxnet.base import data_dir -from nose.tools import * import os import unittest import logging @@ -47,4 +46,3 @@ def test_data_dir(self,): del os.environ['MXNET_HOME'] self.assertEqual(data_dir(), prev_data_dir) - diff --git a/tests/python/unittest/test_contrib_autograd.py b/tests/python/unittest/test_contrib_autograd.py index 1c878e322e7c..c376eb7794f8 100644 --- a/tests/python/unittest/test_contrib_autograd.py +++ b/tests/python/unittest/test_contrib_autograd.py @@ -18,7 +18,7 @@ import mxnet.ndarray as nd from mxnet.contrib.autograd import * from mxnet.test_utils import * -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module def autograd_assert(*args, **kwargs): func = kwargs["func"] @@ -190,7 +190,3 @@ def test_retain_grad(): raise AssertionError( "differentiating the same graph twice without retain_graph should fail") - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_control_flow.py b/tests/python/unittest/test_contrib_control_flow.py index a93c109d11df..b70340240e1c 100644 --- a/tests/python/unittest/test_contrib_control_flow.py +++ b/tests/python/unittest/test_contrib_control_flow.py @@ -1151,9 +1151,9 @@ def cond(inputs, free): ] ) -class TestRNNLayer(gluon.HybridBlock): +class RNNLayer(gluon.HybridBlock): def __init__(self, cell_type, hidden_size, prefix=None, params=None): - super(TestRNNLayer, self).__init__(prefix=prefix, params=params) + super(RNNLayer, self).__init__(prefix=prefix, params=params) self.cell = cell_type(hidden_size, prefix='rnn_') def hybrid_forward(self, F, inputs, states): @@ -1166,7 +1166,7 @@ def check_contrib_rnn(cell_type, num_states): rnn_data = mx.nd.normal(loc=0, scale=1, shape=(5, batch_size, 50)) state_shape = (batch_size, hidden_size) states = [mx.nd.normal(loc=0, scale=1, shape=state_shape) for i in range(num_states)] - layer = TestRNNLayer(cell_type, hidden_size) + layer = RNNLayer(cell_type, hidden_size) layer.initialize(ctx=default_context()) res1 = layer(rnn_data, states) params1 = layer.collect_params() @@ -1184,7 +1184,7 @@ def check_contrib_rnn(cell_type, num_states): {'static_alloc': True}, {'static_alloc': True, 'static_shape': True} ] for config in configs: - layer = TestRNNLayer(cell_type, hidden_size) + layer = RNNLayer(cell_type, hidden_size) layer.initialize(ctx=default_context()) layer.hybridize(**config) res2 = layer(rnn_data, states) @@ -2168,6 +2168,3 @@ def test_foreach_with_unkown_dim(): _, output_shape, _ = outs.infer_shape_partial() assert_allclose((0, 3, 32, 32), output_shape[0]) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_hawkesll.py b/tests/python/unittest/test_contrib_hawkesll.py index a4b1d9de605f..8f02737e2d12 100644 --- a/tests/python/unittest/test_contrib_hawkesll.py +++ b/tests/python/unittest/test_contrib_hawkesll.py @@ -154,8 +154,3 @@ def test_hawkesll_backward_single_mark(): assert np.allclose(beta.grad.asnumpy().sum(), -0.05371582) - -if __name__ == "__main__": - import nose - - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_operator.py b/tests/python/unittest/test_contrib_operator.py index 476dfac24a61..717ce7f20f95 100644 --- a/tests/python/unittest/test_contrib_operator.py +++ b/tests/python/unittest/test_contrib_operator.py @@ -444,7 +444,3 @@ def test_modulated_deformable_convolution(): else: rtol, atol = 0.05, 1e-3 - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_optimizer.py b/tests/python/unittest/test_contrib_optimizer.py index 5f7c51f257b3..aae767202454 100644 --- a/tests/python/unittest/test_contrib_optimizer.py +++ b/tests/python/unittest/test_contrib_optimizer.py @@ -196,6 +196,3 @@ def run_adamw_test(nElem=1, aggregate=False): for nElem in range(6): run_adamw_test(nElem+1) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_stes_op.py b/tests/python/unittest/test_contrib_stes_op.py index 5864ec9db5b1..163ab4a7c9f8 100644 --- a/tests/python/unittest/test_contrib_stes_op.py +++ b/tests/python/unittest/test_contrib_stes_op.py @@ -132,6 +132,3 @@ def test_contrib_sign_ste(): check_ste(net_type_str="SignSTENET", w_init=w_init, hybridize=True, in_data=in_data) check_ste(net_type_str="SignSTENET", w_init=w_init, hybridize=False, in_data=in_data) -if __name__ == '__main__': - import nose - nose.runmodule() \ No newline at end of file diff --git a/tests/python/unittest/test_contrib_svrg_module.py b/tests/python/unittest/test_contrib_svrg_module.py index 79407d15fd7f..f135255753ce 100644 --- a/tests/python/unittest/test_contrib_svrg_module.py +++ b/tests/python/unittest/test_contrib_svrg_module.py @@ -307,7 +307,3 @@ def test_fit(): estimated_mse = 1e-5 assert metric.get()[1] < estimated_mse - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_svrg_optimizer.py b/tests/python/unittest/test_contrib_svrg_optimizer.py index f7d90d12872f..cb6fdcf1218a 100644 --- a/tests/python/unittest/test_contrib_svrg_optimizer.py +++ b/tests/python/unittest/test_contrib_svrg_optimizer.py @@ -95,7 +95,3 @@ def test_kvstore_init_aux_keys(): # updated with AssignmentOptimizer assert same(param_weight_full_init.asnumpy(), np.array([2, 2, 2])) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_contrib_text.py b/tests/python/unittest/test_contrib_text.py index 4072cc84f684..0778e5ace1f7 100644 --- a/tests/python/unittest/test_contrib_text.py +++ b/tests/python/unittest/test_contrib_text.py @@ -792,7 +792,3 @@ def test_get_and_pretrain_file_names(): assertRaises(KeyError, text.embedding.get_pretrained_file_names, 'unknown$$') - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_deferred_compute.py b/tests/python/unittest/test_deferred_compute.py index cebb6908768f..6d250d5fa468 100644 --- a/tests/python/unittest/test_deferred_compute.py +++ b/tests/python/unittest/test_deferred_compute.py @@ -19,11 +19,11 @@ import operator import numpy as np -from nose.tools import raises import mxnet as mx import mxnet._deferred_compute as dc from mxnet.base import MXNetError +import pytest def _all_same(arrays1, arrays2, message=''): @@ -213,7 +213,7 @@ def f(a, *, nd): _all_assert_dc(_dc_simple_setup, f) -@raises(MXNetError) # Should raise NotImplementedError https://github.com/apache/incubator-mxnet/issues/17522 +@pytest.mark.xfail(raises=MXNetError) # Should raise NotImplementedError https://github.com/apache/incubator-mxnet/issues/17522 def test_dc_inplace(): def f(a, *, nd): a[:5] = 0 @@ -245,7 +245,7 @@ def test_dc_get_symbol_called_twice(): assert sym2.list_inputs() == ['a'] -@raises(MXNetError) # Should raise ValueError https://github.com/apache/incubator-mxnet/issues/17522 +@pytest.mark.xfail(raises=MXNetError) # Should raise ValueError https://github.com/apache/incubator-mxnet/issues/17522 def test_dc_set_variable_called_twice(): a = mx.np.arange(10) dc.set_variable(a, mx.sym.var('a')) @@ -342,7 +342,7 @@ def f(a, idx, *, nd): _assert_dc(setup, f, mode=mode) -@raises(TypeError) # Advanced indexing +@pytest.mark.xfail(raises=TypeError) # Advanced indexing def test_dc_list_indexing(): def f(a, *, nd): assert nd is mx.np @@ -352,7 +352,7 @@ def f(a, *, nd): _assert_dc(_dc_simple_setup, f, mode=mode) -@raises(TypeError) # Advanced indexing +@pytest.mark.xfail(raises=TypeError) # Advanced indexing def test_dc_numpy_indexing(): def f(a, *, nd): assert nd is mx.np @@ -430,7 +430,7 @@ def forward(self, x): _assert_dc_gluon(_dc_gluon_simple_setup, net, numpy=True) -@raises(RuntimeError) +@pytest.mark.xfail(raises=RuntimeError) def test_dc_hybridblock_deferred_init_no_infer_shape(): class MyBlock(mx.gluon.HybridBlock): def __init__(self, *, prefix=None, params=None): @@ -496,7 +496,7 @@ def setup(*, nd): _assert_dc_gluon(setup, net, numpy=True) -@raises(RuntimeError) +@pytest.mark.xfail(raises=RuntimeError) def test_dc_hybridblock_symbolblock(): model = mx.gluon.nn.HybridSequential() model.add(mx.gluon.nn.Dense(128, activation='tanh')) @@ -530,7 +530,3 @@ def forward(self, x): _all_same([out], [out_hybrid]) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_dgl_graph.py b/tests/python/unittest/test_dgl_graph.py index 805adc2dac6f..89533fb119aa 100644 --- a/tests/python/unittest/test_dgl_graph.py +++ b/tests/python/unittest/test_dgl_graph.py @@ -240,6 +240,3 @@ def test_adjacency(): assert_array_equal(adj.indices, g.indices) assert_array_equal(adj.data, mx.nd.ones(shape=g.indices.shape)) -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_dlpack.py b/tests/python/unittest/test_dlpack.py index fb64f8d58831..46bdde7d0bcd 100644 --- a/tests/python/unittest/test_dlpack.py +++ b/tests/python/unittest/test_dlpack.py @@ -43,6 +43,3 @@ def from_dlpack_old(dlpack): z = from_dlpack_old(y) assert_almost_equal(x.asnumpy(), z.asnumpy(), rtol=1e-5, atol=1e-5) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_dynamic_shape.py b/tests/python/unittest/test_dynamic_shape.py index 1b043c73256d..b61fbeef6b74 100644 --- a/tests/python/unittest/test_dynamic_shape.py +++ b/tests/python/unittest/test_dynamic_shape.py @@ -48,7 +48,3 @@ def hybrid_forward(self, F, data, index): assert_almost_equal(result.asnumpy(), result_nd) assert_almost_equal(data.grad.asnumpy(), data_grad_nd) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_engine.py b/tests/python/unittest/test_engine.py index 61d94ddbf4ec..fafc6758d892 100644 --- a/tests/python/unittest/test_engine.py +++ b/tests/python/unittest/test_engine.py @@ -15,7 +15,6 @@ # specific language governing permissions and limitations # under the License. -import nose import mxnet as mx import os import unittest @@ -70,8 +69,3 @@ def test_engine_openmp_after_fork(): print("Child omp max threads: {}".format(omp_max_threads)) assert omp_max_threads == 1 - - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_engine_import.py b/tests/python/unittest/test_engine_import.py index 303f3ceb1dee..7675cf836999 100644 --- a/tests/python/unittest/test_engine_import.py +++ b/tests/python/unittest/test_engine_import.py @@ -25,7 +25,7 @@ def test_engine_import(): import mxnet - + engine_types = ['', 'NaiveEngine', 'ThreadedEngine', 'ThreadedEnginePerDevice'] for type in engine_types: @@ -35,7 +35,3 @@ def test_engine_import(): os.environ.pop('MXNET_ENGINE_TYPE', None) reload(mxnet) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_exc_handling.py b/tests/python/unittest/test_exc_handling.py index e3c333705260..8657bec1398c 100644 --- a/tests/python/unittest/test_exc_handling.py +++ b/tests/python/unittest/test_exc_handling.py @@ -18,11 +18,11 @@ import mxnet as mx import numpy as np from mxnet import gluon -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.gluon import nn from mxnet.base import MXNetError from mxnet.test_utils import assert_exception, default_context, set_default_context, use_np -from nose.tools import assert_raises +import pytest @with_seed() @@ -35,7 +35,7 @@ def imperative(exec_numpy=True): c.asnumpy() imperative(exec_numpy=False) - assert_raises(MXNetError, imperative, exec_numpy=True) + pytest.raises(MXNetError, imperative, exec_numpy=True) @with_seed() def test_exc_symbolic(): @@ -69,11 +69,11 @@ def symbolic(exec_backward=True, waitall=True): else: outputs[0].asnumpy() - assert_raises(MXNetError, symbolic, exec_backward=False) - assert_raises(MXNetError, symbolic, exec_backward=True) + pytest.raises(MXNetError, symbolic, exec_backward=False) + pytest.raises(MXNetError, symbolic, exec_backward=True) - assert_raises(MXNetError, symbolic, exec_backward=False, waitall=True) - assert_raises(MXNetError, symbolic, exec_backward=True, waitall=True) + pytest.raises(MXNetError, symbolic, exec_backward=False, waitall=True) + pytest.raises(MXNetError, symbolic, exec_backward=True, waitall=True) @with_seed() def test_exc_gluon(): @@ -93,9 +93,9 @@ def gluon(exec_wait=True, waitall=False): z.wait_to_read() gluon(exec_wait=False) - assert_raises(MXNetError, gluon, exec_wait=True) + pytest.raises(MXNetError, gluon, exec_wait=True) - assert_raises(MXNetError, gluon, waitall=True) + pytest.raises(MXNetError, gluon, waitall=True) @with_seed() def test_exc_multiple_waits(): @@ -152,8 +152,8 @@ def mutable_var_check(waitall=False): mx.nd.waitall() else: a.asnumpy() - assert_raises(MXNetError, mutable_var_check, waitall=False) - assert_raises(MXNetError, mutable_var_check, waitall=True) + pytest.raises(MXNetError, mutable_var_check, waitall=False) + pytest.raises(MXNetError, mutable_var_check, waitall=True) @with_seed() def test_multiple_waitalls(): @@ -189,16 +189,16 @@ def check_resize(): img = mx.nd.ones((1200, 1600, 3)) img = mx.image.imresize(img, 320, 320, interp=-1) img.asnumpy() - assert_raises(MXNetError, check_resize) + pytest.raises(MXNetError, check_resize) @with_seed() def test_np_reshape_exception(): a = mx.np.ones((10, 10)) a.reshape((-1,)).asnumpy() # Check no-raise - assert_raises(MXNetError, lambda: a.reshape((1,))) - assert_raises(MXNetError, lambda: mx.np.reshape(a, (1,))) - assert_raises(MXNetError, lambda: mx.np.reshape(a, (-1, 3))) + pytest.raises(MXNetError, lambda: a.reshape((1,))) + pytest.raises(MXNetError, lambda: mx.np.reshape(a, (1,))) + pytest.raises(MXNetError, lambda: mx.np.reshape(a, (-1, 3))) @with_seed() @@ -208,10 +208,6 @@ def test_np_random_incorrect_named_arguments(): for op_name in random_ops: op = getattr(mx.np.random, op_name, None) assert op is not None - assert_raises(TypeError, op, shape=()) - assert_raises(TypeError, op, shape=None) + pytest.raises(TypeError, op, shape=()) + pytest.raises(TypeError, op, shape=None) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_executor.py b/tests/python/unittest/test_executor.py index 2bc696fd4e43..300e4b2590c8 100644 --- a/tests/python/unittest/test_executor.py +++ b/tests/python/unittest/test_executor.py @@ -17,7 +17,7 @@ import numpy as np import mxnet as mx -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.test_utils import assert_almost_equal @@ -164,7 +164,3 @@ def test_reshape(): # weight ndarray is shared between exe and new_exe assert np.all(new_exe.arg_arrays[1].asnumpy() == 1) - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon.py b/tests/python/unittest/test_gluon.py index 11e8fe9a0e3f..b9a329fde2fe 100644 --- a/tests/python/unittest/test_gluon.py +++ b/tests/python/unittest/test_gluon.py @@ -27,11 +27,11 @@ from mxnet.ndarray.ndarray import _STORAGE_TYPE_STR_TO_ID from mxnet.test_utils import use_np import mxnet.numpy as _mx_np -from common import (setup_module, with_seed, assertRaises, teardown, +from common import (setup_module, with_seed, assertRaises, teardown_module, assert_raises_cudnn_not_satisfied) import numpy as np from numpy.testing import assert_array_equal -from nose.tools import raises, assert_raises +import pytest from copy import deepcopy import warnings import json @@ -55,12 +55,12 @@ def test_parameter(): assert p.list_ctx() == [mx.cpu(1), mx.cpu(2)] @with_seed() -@raises(AssertionError) +@pytest.mark.xfail(raises=AssertionError) def test_invalid_parameter_stype(): p = gluon.Parameter('weight', shape=(10, 10), stype='invalid') @with_seed() -@raises(AssertionError) +@pytest.mark.xfail(raises=AssertionError) def test_invalid_parameter_grad_stype(): p = gluon.Parameter('weight', shape=(10, 10), grad_stype='invalid') @@ -425,7 +425,7 @@ def hybrid_forward(self, F, x): assert np.dtype(prediction.dtype) == np.dtype(np.float32) @with_seed() -@raises(AssertionError) +@pytest.mark.xfail(raises=AssertionError) def test_sparse_symbol_block(): data = mx.sym.var('data') weight = mx.sym.var('weight', stype='row_sparse') @@ -435,7 +435,7 @@ def test_sparse_symbol_block(): net = gluon.SymbolBlock(out, data) @with_seed() -@raises(RuntimeError) +@pytest.mark.xfail(raises=RuntimeError) def test_sparse_hybrid_block(): params = gluon.ParameterDict('net_') params.get('weight', shape=(5,5), stype='row_sparse', dtype='float32') @@ -502,17 +502,17 @@ def hybrid_forward(self, F, a, b): foo = FooNested() if do_hybridize: foo.hybridize() - assert_raises(ValueError, foo, None, None) + pytest.raises(ValueError, foo, None, None) # Make sure the ValueError is correctly raised foo = FooNested() foo.hybridize() foo(None, mx.nd.ones((10,))) # Pass for the first time to initialize the cached op - assert_raises(ValueError, lambda: foo(mx.nd.ones((10,)), mx.nd.ones((10,)))) + pytest.raises(ValueError, lambda: foo(mx.nd.ones((10,)), mx.nd.ones((10,)))) foo = FooNested() - assert_raises(ValueError, lambda: foo(mx.nd.ones((10,)), mx.sym.var('a'))) + pytest.raises(ValueError, lambda: foo(mx.nd.ones((10,)), mx.sym.var('a'))) foo = FooNested() - assert_raises(ValueError, lambda: foo(mx.sym.var('a'), mx.nd.ones((10,)))) + pytest.raises(ValueError, lambda: foo(mx.sym.var('a'), mx.nd.ones((10,)))) # Test the case of the default values foo1 = FooDefault() @@ -530,7 +530,7 @@ def hybrid_forward(self, F, a, b): out1 = foo1(mx.nd.ones((10,)), None) out2 = foo1(mx.nd.ones((10,))) assert_almost_equal(out1.asnumpy(), out2.asnumpy()) - assert_raises(ValueError, lambda: foo1(mx.nd.ones((10,)), mx.nd.ones((10,)))) + pytest.raises(ValueError, lambda: foo1(mx.nd.ones((10,)), mx.nd.ones((10,)))) @with_seed() @@ -568,13 +568,13 @@ def forward(self, a, b): # 4. Allow mixing of cpu_pinned and cpu foo_hybrid = FooHybrid() foo_hybrid.hybridize() - assert_raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,)), 1)) + pytest.raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,)), 1)) foo_hybrid = FooHybrid() foo_hybrid.hybridize() - assert_raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,)), mx.sym.var('a'))) + pytest.raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,)), mx.sym.var('a'))) foo_hybrid = FooHybrid() foo_hybrid.hybridize() - assert_raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,), ctx=mx.cpu(1)), + pytest.raises(ValueError, lambda: foo_hybrid(mx.nd.ones((10,), ctx=mx.cpu(1)), mx.nd.ones((10,), ctx=mx.cpu(2)))) @@ -901,7 +901,7 @@ def test_layernorm(): layer.initialize() if hybridize: layer.hybridize() - assert_raises(MXNetError, lambda: layer(mx.nd.ones((2, 11)))) + pytest.raises(MXNetError, lambda: layer(mx.nd.ones((2, 11)))) @with_seed() def test_groupnorm(): @@ -1024,7 +1024,7 @@ def test_block_attr_hidden(): b.a = 1 -@raises(TypeError) +@pytest.mark.xfail(raises=TypeError) @with_seed() def test_block_attr_block(): b = gluon.Block() @@ -1034,7 +1034,7 @@ def test_block_attr_block(): b.b = (2,) -@raises(TypeError) +@pytest.mark.xfail(raises=TypeError) @with_seed() def test_block_attr_param(): b = gluon.Block() @@ -1887,7 +1887,7 @@ def test_summary(): net3.summary(mx.nd.ones((80, 32, 5)), begin_state) net.hybridize() - assert_raises(AssertionError, net.summary, mx.nd.ones((32, 3, 224, 224))) + pytest.raises(AssertionError, net.summary, mx.nd.ones((32, 3, 224, 224))) @with_seed() @@ -3216,46 +3216,3 @@ def hybrid_forward(self, F, x): mx.test_utils.assert_almost_equal(grad1, grad2) -def test_getitem_hybridized(): - class picking_np(gluon.HybridBlock): - def __init__(self, prefix=None, params=None): - super().__init__(prefix=prefix, params=params) - def hybrid_forward(self, F, sequence, pick_ids): - """ - new implementation in deep numpy - """ - idx_arange = F.npx.arange_like(pick_ids.reshape((-1, )), axis=0) - batch_idx = F.np.floor(idx_arange / 2).astype(np.int32) - - encoded = sequence[batch_idx, pick_ids.reshape((-1,))] - encoded = F.npx.reshape_like(encoded, pick_ids, lhs_begin=-2, lhs_end=-1, rhs_begin=0) - return encoded - - sequence = mx.nd.array(np.random.normal(0, 1, (8, 32, 768)), dtype=np.float32) - # pick_ids: [batch_size, picked_index] - pick_ids = mx.nd.random.randint(0, 32, (8,2), dtype=np.int32) - - mx.npx.set_np() - picker_np = picking_np() - seq_np = sequence.as_np_ndarray() - np_output = picker_np(seq_np, pick_ids.as_np_ndarray()) - seq_np.attach_grad() - with mx.autograd.record(): - z = picker_np(seq_np, pick_ids.as_np_ndarray()) - z.backward() - - picker_np.initialize() - picker_np.hybridize() - nd_output_hybridized = picker_np(sequence.as_np_ndarray(), pick_ids.as_np_ndarray()) - seq_np_hybridized = sequence.as_np_ndarray() - seq_np_hybridized.attach_grad() - with mx.autograd.record(): - z_hybridized = picker_np(seq_np_hybridized, pick_ids.as_np_ndarray()) - z_hybridized.backward() - - assert_allclose(nd_output_hybridized.asnumpy(), np_output.asnumpy(), rtol=1e-5, atol=1e-5) - assert_allclose(seq_np.grad.asnumpy(), seq_np_hybridized.grad.asnumpy(), rtol=1e-5, atol=1e-5) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_batch_processor.py b/tests/python/unittest/test_gluon_batch_processor.py index 8604713fc129..952ed1c4a0da 100644 --- a/tests/python/unittest/test_gluon_batch_processor.py +++ b/tests/python/unittest/test_gluon_batch_processor.py @@ -27,7 +27,7 @@ from mxnet.gluon.contrib.estimator import * from mxnet.gluon.contrib.estimator.event_handler import * from mxnet.gluon.contrib.estimator.batch_processor import BatchProcessor -from nose.tools import assert_raises +import pytest def _get_test_network(): net = nn.Sequential() @@ -66,12 +66,12 @@ def test_batch_processor_fit(): est.fit(train_data=dataloader, epochs=num_epochs) - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=dataiter, epochs=num_epochs) # Input NDArray - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=[mx.nd.ones(shape=(10, 3))], epochs=num_epochs) @@ -105,12 +105,12 @@ def test_batch_processor_validation(): val_metrics = est.val_metrics validation_handler = ValidationHandler(val_data=dataloader, eval_fn=est.evaluate) - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=dataiter, val_data=dataiter, epochs=num_epochs) # Input NDArray - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=[mx.nd.ones(shape=(10, 3))], val_data=[mx.nd.ones(shape=(10, 3))], epochs=num_epochs) diff --git a/tests/python/unittest/test_gluon_contrib.py b/tests/python/unittest/test_gluon_contrib.py index 0ed0d4e8a545..a69b0230c3c8 100644 --- a/tests/python/unittest/test_gluon_contrib.py +++ b/tests/python/unittest/test_gluon_contrib.py @@ -25,7 +25,7 @@ Concurrent, HybridConcurrent, Identity, SparseEmbedding, PixelShuffle1D, PixelShuffle2D, PixelShuffle3D) from mxnet.test_utils import almost_equal, default_context, assert_almost_equal, assert_allclose -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module import numpy as np @@ -314,9 +314,9 @@ def test_sampler(): assert list(interval_sampler) == [0, 3, 6, 9] -class TestRNNLayer(gluon.HybridBlock): +class RNNLayer(gluon.HybridBlock): def __init__(self, cell_type, hidden_size, layout, prefix=None, params=None): - super(TestRNNLayer, self).__init__(prefix=prefix, params=params) + super(RNNLayer, self).__init__(prefix=prefix, params=params) self.cell = cell_type(hidden_size, prefix='rnn_') self.layout = layout @@ -370,7 +370,7 @@ def check_unroll(cell_type, num_states, layout): if valid_length is None: valid_length = [] for config in configs: - layer = TestRNNLayer(cell_type, hidden_size, layout) + layer = RNNLayer(cell_type, hidden_size, layout) layer.initialize(ctx=default_context()) config(layer) res2, states2 = layer(rnn_data, states, valid_length) @@ -436,7 +436,3 @@ def test_ModulatedDeformableConvolution(): with mx.autograd.record(): y = net(x) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_data.py b/tests/python/unittest/test_gluon_data.py index 29197bd58f6c..e6e3caebdf16 100644 --- a/tests/python/unittest/test_gluon_data.py +++ b/tests/python/unittest/test_gluon_data.py @@ -23,7 +23,7 @@ import random from mxnet import gluon import platform -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.gluon.data import DataLoader import mxnet.ndarray as nd from mxnet import context @@ -382,7 +382,3 @@ def test_dataloader_scope(): assert item is not None - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_data_vision.py b/tests/python/unittest/test_gluon_data_vision.py index b53dbf0687d3..d810f32b0afa 100644 --- a/tests/python/unittest/test_gluon_data_vision.py +++ b/tests/python/unittest/test_gluon_data_vision.py @@ -25,7 +25,7 @@ from mxnet.gluon.data.vision import transforms from mxnet import image from mxnet.test_utils import * -from common import assertRaises, setup_module, with_seed, teardown +from common import assertRaises, setup_module, with_seed, teardown_module import numpy as np @@ -42,12 +42,12 @@ def test_to_tensor(): out_nd = transforms.ToTensor()(nd.array(data_in, dtype='uint8')) assert_almost_equal(out_nd.asnumpy(), np.transpose( data_in.astype(dtype=np.float32) / 255.0, (0, 3, 1, 2))) - + # Invalid Input invalid_data_in = nd.random.uniform(0, 255, (5, 5, 300, 300, 3)).astype(dtype=np.uint8) transformer = transforms.ToTensor() assertRaises(MXNetError, transformer, invalid_data_in) - + # Bounds (0->0, 255->1) data_in = np.zeros((10, 20, 3)).astype(dtype=np.uint8) out_nd = transforms.ToTensor()(nd.array(data_in, dtype='uint8')) @@ -126,7 +126,7 @@ def _test_resize_with_diff_type(dtype): assertRaises(MXNetError, invalid_transform, data_in) for dtype in ['uint8', 'float32', 'float64']: - _test_resize_with_diff_type(dtype) + _test_resize_with_diff_type(dtype) @with_seed() @@ -159,7 +159,7 @@ def _test_crop_resize_with_diff_type(dtype): # test with resize height and width should be greater than 0 transformer = transforms.CropResize(0, 0, 100, 50, (-25, 25), 1) assertRaises(MXNetError, transformer, data_in) - # test height and width should be greater than 0 + # test height and width should be greater than 0 transformer = transforms.CropResize(0, 0, -100, -50) assertRaises(MXNetError, transformer, data_in) # test cropped area is bigger than input data @@ -168,7 +168,7 @@ def _test_crop_resize_with_diff_type(dtype): assertRaises(MXNetError, transformer, data_bath_in) for dtype in ['uint8', 'float32', 'float64']: - _test_crop_resize_with_diff_type(dtype) + _test_crop_resize_with_diff_type(dtype) # test nd.image.crop backward def test_crop_backward(test_nd_arr, TestCase): @@ -288,7 +288,7 @@ def test_random_rotation(): @with_seed() def test_random_transforms(): from mxnet.gluon.data.vision import transforms - + tmp_t = transforms.Compose([transforms.Resize(300), transforms.RandomResizedCrop(224)]) transform = transforms.Compose([transforms.RandomApply(tmp_t, 0.5)]) @@ -302,6 +302,3 @@ def test_random_transforms(): assert_almost_equal(num_apply/float(iteration), 0.5, 0.1) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_estimator.py b/tests/python/unittest/test_gluon_estimator.py index 2c00b1609112..e33aa74b3ca7 100644 --- a/tests/python/unittest/test_gluon_estimator.py +++ b/tests/python/unittest/test_gluon_estimator.py @@ -20,13 +20,13 @@ import sys import unittest import warnings +import pytest import mxnet as mx from mxnet import gluon from mxnet.gluon import nn from mxnet.gluon.contrib.estimator import * from mxnet.gluon.contrib.estimator.event_handler import * -from nose.tools import assert_raises def _get_test_network(params=None): @@ -70,12 +70,12 @@ def test_fit(): est.fit(train_data=dataloader, epochs=num_epochs) - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=dataiter, epochs=num_epochs) # Input NDArray - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=[mx.nd.ones(shape=(10, 3))], epochs=num_epochs) @@ -107,12 +107,12 @@ def test_validation(): val_metrics = est.val_metrics validation_handler = ValidationHandler(val_data=dataloader, eval_fn=est.evaluate) - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=dataiter, val_data=dataiter, epochs=num_epochs) # Input NDArray - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=[mx.nd.ones(shape=(10, 3))], val_data=[mx.nd.ones(shape=(10, 3))], epochs=num_epochs) @@ -180,7 +180,7 @@ def test_trainer(): # input invalid trainer trainer = 'sgd' - with assert_raises(ValueError): + with pytest.raises(ValueError): est = Estimator(net=net, loss=loss, train_metrics=acc, @@ -215,7 +215,7 @@ def test_metric(): est.fit(train_data=train_data, epochs=num_epochs) # input invalid metric - with assert_raises(ValueError): + with pytest.raises(ValueError): est = Estimator(net=net, loss=loss, train_metrics='acc', @@ -238,7 +238,7 @@ def test_loss(): net.initialize(ctx=ctx) trainer = gluon.Trainer(net.collect_params(), 'sgd', {'learning_rate': 0.001}) # input invalid loss - with assert_raises(ValueError): + with pytest.raises(ValueError): est = Estimator(net=net, loss='mse', train_metrics=acc, @@ -264,13 +264,13 @@ def test_context(): train_metrics=metrics, context=ctx) # input invalid context - with assert_raises(ValueError): + with pytest.raises(ValueError): est = Estimator(net=net, loss=loss, train_metrics=metrics, context='cpu') - with assert_raises(AssertionError): + with pytest.raises(AssertionError): est = Estimator(net=net, loss=loss, train_metrics=metrics, @@ -360,7 +360,7 @@ def test_default_handlers(): # handler with mixed metrics, some handler use metrics prepared by estimator # some handler use metrics user prepared logging = LoggingHandler(metrics=[mx.metric.RMSE("val acc")]) - with assert_raises(ValueError): + with pytest.raises(ValueError): est.fit(train_data=train_data, epochs=num_epochs, event_handlers=[logging]) # test handler order @@ -394,7 +394,7 @@ def test_val_net(): val_loss=val_loss, val_net=val_net) - with assert_raises(RuntimeError): + with pytest.raises(RuntimeError): est.fit(train_data=dataloader, val_data=dataloader, epochs=num_epochs) diff --git a/tests/python/unittest/test_gluon_event_handler.py b/tests/python/unittest/test_gluon_event_handler.py index c81d29157e7f..a07282cd46dd 100644 --- a/tests/python/unittest/test_gluon_event_handler.py +++ b/tests/python/unittest/test_gluon_event_handler.py @@ -34,7 +34,7 @@ except ImportError: from io import StringIO -class TestAxisArrayDataset(Dataset): +class AxisArrayDataset(Dataset): def __init__(self, * args): self._length = len(args[1]) self._data = [] @@ -50,7 +50,7 @@ def __getitem__(self, idx): def __len__(self): return self._length -class TestHandler(EpochEnd): +class Handler(EpochEnd): def __init__(self): pass @@ -73,7 +73,7 @@ def _get_test_data(in_size=32): def _get_batch_axis_test_data(in_size=32): data = nd.ones((100, in_size)) label = nd.zeros((1, in_size)) - data_arr = TestAxisArrayDataset(data, label) + data_arr = AxisArrayDataset(data, label) return mx.gluon.data.DataLoader(data_arr, batch_size=8) def test_checkpoint_handler(): @@ -264,8 +264,8 @@ def test_logging_interval(): info_len = 0 for info in log_info_list: match = re.match( - '(\[Epoch \d+\]\[Batch \d+\]\[Samples \d+\] time\/interval: \d+.\d+s' + - ' training accuracy: \d+.\d+)', info) + r'(\[Epoch \d+\]\[Batch \d+\]\[Samples \d+\] time\/interval: \d+.\d+s' + + r' training accuracy: \d+.\d+)', info) if match: info_len += 1 @@ -287,8 +287,8 @@ def test_logging_interval(): info_len = 0 for info in log_info_list: match = re.match( - '(\[Epoch \d+\]\[Batch \d+\]\[Samples \d+\] time\/interval: \d+.\d+s' + - ' training accuracy: \d+.\d+)', info) + r'(\[Epoch \d+\]\[Batch \d+\]\[Samples \d+\] time\/interval: \d+.\d+s' + + r' training accuracy: \d+.\d+)', info) if match: info_len += 1 @@ -319,7 +319,7 @@ def test_validation_handler(): est = estimator.Estimator(net, loss=ce_loss, train_metrics=acc) val_handler = ValidationHandler(val_data=test_data, eval_fn=est.evaluate, - event_handlers=TestHandler()) + event_handlers=Handler()) est.fit(train_data=test_data, val_data=test_data, event_handlers=[val_handler], epochs=2) diff --git a/tests/python/unittest/test_gluon_model_zoo.py b/tests/python/unittest/test_gluon_model_zoo.py index d53dd403a5b8..214f44dd0854 100644 --- a/tests/python/unittest/test_gluon_model_zoo.py +++ b/tests/python/unittest/test_gluon_model_zoo.py @@ -19,8 +19,9 @@ import mxnet as mx from mxnet.gluon.model_zoo.vision import get_model import sys -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module import multiprocessing +import pytest def eprint(*args, **kwargs): @@ -55,6 +56,7 @@ def parallel_download(model_name): print(type(model)) @with_seed() +@pytest.mark.skip(reason='MXNet is not yet safe for forking. Tracked in #17782.') def test_parallel_download(): processes = [] name = 'mobilenetv2_0.25' @@ -66,6 +68,3 @@ def test_parallel_download(): for p in processes: p.join() -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_rnn.py b/tests/python/unittest/test_gluon_rnn.py index 4be96fc1935b..c05719420384 100644 --- a/tests/python/unittest/test_gluon_rnn.py +++ b/tests/python/unittest/test_gluon_rnn.py @@ -938,7 +938,3 @@ def hybrid_forward(self, F, inputs, valid_len): _check_bidirectional_unroll_valid_length(1) _check_bidirectional_unroll_valid_length(3) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_gluon_trainer.py b/tests/python/unittest/test_gluon_trainer.py index 350700cc129f..414b15c3b3f2 100644 --- a/tests/python/unittest/test_gluon_trainer.py +++ b/tests/python/unittest/test_gluon_trainer.py @@ -24,7 +24,7 @@ from mxnet.test_utils import assert_almost_equal from common import setup_module, with_seed, assertRaises from copy import deepcopy -from nose.tools import raises, assert_raises +import pytest def dict_equ(a, b): assert set(a) == set(b) @@ -32,7 +32,7 @@ def dict_equ(a, b): assert (a[k].asnumpy() == b[k].asnumpy()).all() @with_seed() -@raises(RuntimeError) +@pytest.mark.xfail(raises=RuntimeError) def test_multi_trainer(): x = gluon.Parameter('x', shape=(10,), stype='row_sparse') x.initialize() @@ -78,7 +78,7 @@ def test_trainer_with_teststore(): # Expect exceptions if update_on_kvstore is set to True, # because TestStore does not support that invalid_trainer = gluon.Trainer([x], 'sgd', kvstore=kv, update_on_kvstore=True) - assert_raises(ValueError, invalid_trainer._init_kvstore) + pytest.raises(ValueError, invalid_trainer._init_kvstore) @with_seed() def test_trainer(): @@ -110,8 +110,8 @@ def test_trainer(): dict_equ(trainer._kvstore._updater.states, states) assert trainer._optimizer == trainer._kvstore._updater.optimizer # invalid usage of update and allreduce_grads if update_on_kvstore - assert_raises(AssertionError, trainer.update, 1) - assert_raises(AssertionError, trainer.allreduce_grads) + pytest.raises(AssertionError, trainer.update, 1) + pytest.raises(AssertionError, trainer.allreduce_grads) else: for updater in trainer._updaters: dict_equ(updater.states, states) diff --git a/tests/python/unittest/test_gluon_utils.py b/tests/python/unittest/test_gluon_utils.py index bc816b1794ee..4e37596fab0b 100644 --- a/tests/python/unittest/test_gluon_utils.py +++ b/tests/python/unittest/test_gluon_utils.py @@ -29,7 +29,7 @@ import mock import mxnet as mx import requests -from nose.tools import raises +import pytest class MockResponse(requests.Response): @@ -40,7 +40,7 @@ def __init__(self, status_code, content): self.raw = io.BytesIO(content.encode('utf-8')) -@raises(Exception) +@pytest.mark.xfail(raises=Exception) @mock.patch( 'requests.get', mock.Mock(side_effect=requests.exceptions.ConnectionError)) def test_download_retries(): diff --git a/tests/python/unittest/test_higher_order_grad.py b/tests/python/unittest/test_higher_order_grad.py index ad31c34bd590..28357360bc41 100644 --- a/tests/python/unittest/test_higher_order_grad.py +++ b/tests/python/unittest/test_higher_order_grad.py @@ -22,8 +22,6 @@ from operator import mul import random -from nose.tools import ok_ - from common import with_seed import mxnet from mxnet import nd, autograd, gluon @@ -648,18 +646,18 @@ def test_dense_backward_flatten(): w_grad_grad_e = nd.dot(o_y, o_x_grad, transpose_a=True) x_grad_e = nd.dot(o_y, w) x_grad_grad_e = nd.dot(o_y, o_w_grad) - ok_(w_grad.shape == w.shape) - ok_(w_grad_grad.shape == w.shape) - ok_(x_grad.shape == x.shape) - ok_(x_grad_grad.shape == x.shape) + assert w_grad.shape == w.shape + assert w_grad_grad.shape == w.shape + assert x_grad.shape == x.shape + assert x_grad_grad.shape == x.shape w_grad_check = same(flatten2d_right(w_grad), flatten2d_right(w_grad_e)) w_grad_grad_check = same(flatten2d_right(w_grad_grad), flatten2d_right(w_grad_grad_e)) x_grad_check = same(flatten2d_right(x_grad), flatten2d_right(x_grad_e)) x_grad_grad_check = same(flatten2d_right(x_grad_grad), flatten2d_right(x_grad_grad_e)) - ok_(x_grad_check) - ok_(w_grad_check) - ok_(x_grad_grad_check) - ok_(w_grad_grad_check) + assert x_grad_check + assert w_grad_check + assert x_grad_grad_check + assert w_grad_grad_check @with_seed() def test_dense_backward_no_flatten(): @@ -701,12 +699,8 @@ def test_dense_backward_no_flatten(): w_grad_grad_check = same(flatten2d_left(w_grad_grad), flatten2d_left(w_grad_grad_e)) x_grad_check = same(flatten2d_left(x_grad), flatten2d_left(x_grad_e)) x_grad_grad_check = same(flatten2d_left(x_grad_grad), flatten2d_left(x_grad_grad_e)) - ok_(x_grad_check) - ok_(w_grad_check) - ok_(x_grad_grad_check) - ok_(w_grad_grad_check) - + assert x_grad_check + assert w_grad_check + assert x_grad_grad_check + assert w_grad_grad_check -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_image.py b/tests/python/unittest/test_image.py index 033b8e5aab04..d9fe0b71809d 100644 --- a/tests/python/unittest/test_image.py +++ b/tests/python/unittest/test_image.py @@ -15,6 +15,7 @@ # specific language governing permissions and limitations # under the License. +import os import mxnet as mx import numpy as np import scipy.ndimage @@ -23,8 +24,7 @@ import shutil import tempfile import unittest - -from nose.tools import raises +import pytest def _get_data(url, dirname): @@ -111,27 +111,23 @@ def _test_imageiter_last_batch(imageiter_list, assert_data_shape): class TestImage(unittest.TestCase): IMAGES_URL = "http://data.mxnet.io/data/test_images.tar.gz" - IMAGES = [] - IMAGES_DIR = None - - @classmethod - def setupClass(cls): - cls.IMAGES_DIR = tempfile.mkdtemp() - cls.IMAGES = _get_data(cls.IMAGES_URL, cls.IMAGES_DIR) - print("Loaded {} images".format(len(cls.IMAGES))) - - @classmethod - def teardownClass(cls): - if cls.IMAGES_DIR: - print("cleanup {}".format(cls.IMAGES_DIR)) - shutil.rmtree(cls.IMAGES_DIR) - - @raises(mx.base.MXNetError) + + def setUp(self): + self.IMAGES_DIR = tempfile.mkdtemp() + self.IMAGES = _get_data(self.IMAGES_URL, self.IMAGES_DIR) + print("Loaded {} images".format(len(self.IMAGES))) + + def tearDown(self): + if self.IMAGES_DIR: + print("cleanup {}".format(self.IMAGES_DIR)) + shutil.rmtree(self.IMAGES_DIR) + + @pytest.mark.xfail(raises=mx.base.MXNetError) def test_imread_not_found(self): x = mx.img.image.imread("/139810923jadjsajlskd.___adskj/blah.jpg") def test_imread_vs_imdecode(self): - for img in TestImage.IMAGES: + for img in self.IMAGES: with open(img, 'rb') as fp: str_image = fp.read() image = mx.image.imdecode(str_image, to_rgb=0) @@ -143,7 +139,7 @@ def test_imdecode(self): import cv2 except ImportError: raise unittest.SkipTest("Unable to import cv2.") - for img in TestImage.IMAGES: + for img in self.IMAGES: with open(img, 'rb') as fp: str_image = fp.read() image = mx.image.imdecode(str_image, to_rgb=0) @@ -155,18 +151,18 @@ def test_imdecode_bytearray(self): import cv2 except ImportError: return - for img in TestImage.IMAGES: + for img in self.IMAGES: with open(img, 'rb') as fp: str_image = bytearray(fp.read()) image = mx.image.imdecode(str_image, to_rgb=0) cv_image = cv2.imread(img) assert_almost_equal(image.asnumpy(), cv_image) - @raises(mx.base.MXNetError) + @pytest.mark.xfail(raises=mx.base.MXNetError) def test_imdecode_empty_buffer(self): mx.image.imdecode(b'', to_rgb=0) - @raises(mx.base.MXNetError) + @pytest.mark.xfail(raises=mx.base.MXNetError) def test_imdecode_invalid_image(self): image = mx.image.imdecode(b'clearly not image content') assert_equal(image, None) @@ -182,7 +178,7 @@ def test_resize_short(self): import cv2 except ImportError: raise unittest.SkipTest("Unable to import cv2") - for img in TestImage.IMAGES: + for img in self.IMAGES: cv_img = cv2.imread(img) mx_img = mx.nd.array(cv_img[:, :, (2, 1, 0)]) h, w, _ = cv_img.shape @@ -204,7 +200,7 @@ def test_imresize(self): import cv2 except ImportError: raise unittest.SkipTest("Unable to import cv2") - for img in TestImage.IMAGES: + for img in self.IMAGES: cv_img = cv2.imread(img) mx_img = mx.nd.array(cv_img[:, :, (2, 1, 0)]) new_h = np.random.randint(1, 1000) @@ -229,10 +225,11 @@ def test_color_normalize(self): assert_almost_equal(mx_result.asnumpy(), (src - mean) / std, atol=1e-3) def test_imageiter(self): - im_list = [[np.random.randint(0, 5), x] for x in TestImage.IMAGES] - fname = './data/test_imageiter.lst' + print(self.IMAGES) + im_list = [[np.random.randint(0, 5), x] for x in self.IMAGES] + fname = os.path.join(self.IMAGES_DIR, 'test_imageiter.lst') file_list = ['\t'.join([str(k), str(np.random.randint(0, 5)), x]) - for k, x in enumerate(TestImage.IMAGES)] + for k, x in enumerate(self.IMAGES)] with open(fname, 'w') as f: for line in file_list: f.write(line + '\n') @@ -244,15 +241,15 @@ def test_imageiter(self): path_imglist = fname if test == 'path_imglist' else None imageiter_list = [ mx.image.ImageIter(2, (3, 224, 224), label_width=1, imglist=imglist, - path_imglist=path_imglist, path_root='', dtype=dtype), + path_imglist=path_imglist, path_root=self.IMAGES_DIR, dtype=dtype), mx.image.ImageIter(3, (3, 224, 224), label_width=1, imglist=imglist, - path_imglist=path_imglist, path_root='', dtype=dtype, last_batch_handle='discard'), + path_imglist=path_imglist, path_root=self.IMAGES_DIR, dtype=dtype, last_batch_handle='discard'), mx.image.ImageIter(3, (3, 224, 224), label_width=1, imglist=imglist, - path_imglist=path_imglist, path_root='', dtype=dtype, last_batch_handle='pad'), + path_imglist=path_imglist, path_root=self.IMAGES_DIR, dtype=dtype, last_batch_handle='pad'), mx.image.ImageIter(3, (3, 224, 224), label_width=1, imglist=imglist, - path_imglist=path_imglist, path_root='', dtype=dtype, last_batch_handle='roll_over'), + path_imglist=path_imglist, path_root=self.IMAGES_DIR, dtype=dtype, last_batch_handle='roll_over'), mx.image.ImageIter(3, (3, 224, 224), label_width=1, imglist=imglist, shuffle=True, - path_imglist=path_imglist, path_root='', dtype=dtype, last_batch_handle='pad') + path_imglist=path_imglist, path_root=self.IMAGES_DIR, dtype=dtype, last_batch_handle='pad') ] _test_imageiter_last_batch(imageiter_list, (2, 3, 224, 224)) @@ -262,7 +259,7 @@ def test_copyMakeBorder(self): import cv2 except ImportError: raise unittest.SkipTest("Unable to import cv2") - for img in TestImage.IMAGES: + for img in self.IMAGES: cv_img = cv2.imread(img) mx_img = mx.nd.array(cv_img) top = np.random.randint(1, 10) @@ -296,34 +293,34 @@ def test_augmenters(self): # only test if all augmenters will work # TODO(Joshua Zhang): verify the augmenter outputs - im_list = [[0, x] for x in TestImage.IMAGES] + im_list = [[0, x] for x in self.IMAGES] test_iter = mx.image.ImageIter(2, (3, 224, 224), label_width=1, imglist=im_list, resize=640, rand_crop=True, rand_resize=True, rand_mirror=True, mean=True, std=np.array([1.1, 1.03, 1.05]), brightness=0.1, contrast=0.1, saturation=0.1, - hue=0.1, pca_noise=0.1, rand_gray=0.2, inter_method=10, path_root='', shuffle=True) + hue=0.1, pca_noise=0.1, rand_gray=0.2, inter_method=10, path_root=self.IMAGES_DIR, shuffle=True) for batch in test_iter: pass def test_image_detiter(self): - im_list = [_generate_objects() + [x] for x in TestImage.IMAGES] - det_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root='') + im_list = [_generate_objects() + [x] for x in self.IMAGES] + det_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root=self.IMAGES_DIR) for _ in range(3): for _ in det_iter: pass det_iter.reset() - val_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root='') + val_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root=self.IMAGES_DIR) det_iter = val_iter.sync_label_shape(det_iter) assert det_iter.data_shape == val_iter.data_shape assert det_iter.label_shape == val_iter.label_shape # test batch_size is not divisible by number of images - det_iter = mx.image.ImageDetIter(4, (3, 300, 300), imglist=im_list, path_root='') + det_iter = mx.image.ImageDetIter(4, (3, 300, 300), imglist=im_list, path_root=self.IMAGES_DIR) for _ in det_iter: pass # test file list with last batch handle - fname = './data/test_imagedetiter.lst' - im_list = [[k] + _generate_objects() + [x] for k, x in enumerate(TestImage.IMAGES)] + fname = os.path.join(self.IMAGES_DIR, 'test_imagedetiter.lst') + im_list = [[k] + _generate_objects() + [x] for k, x in enumerate(self.IMAGES)] with open(fname, 'w') as f: for line in im_list: line = '\t'.join([str(k) for k in line]) @@ -331,23 +328,23 @@ def test_image_detiter(self): imageiter_list = [ mx.image.ImageDetIter(2, (3, 400, 400), - path_imglist=fname, path_root=''), + path_imglist=fname, path_root=self.IMAGES_DIR), mx.image.ImageDetIter(3, (3, 400, 400), - path_imglist=fname, path_root='', last_batch_handle='discard'), + path_imglist=fname, path_root=self.IMAGES_DIR, last_batch_handle='discard'), mx.image.ImageDetIter(3, (3, 400, 400), - path_imglist=fname, path_root='', last_batch_handle='pad'), + path_imglist=fname, path_root=self.IMAGES_DIR, last_batch_handle='pad'), mx.image.ImageDetIter(3, (3, 400, 400), - path_imglist=fname, path_root='', last_batch_handle='roll_over'), + path_imglist=fname, path_root=self.IMAGES_DIR, last_batch_handle='roll_over'), mx.image.ImageDetIter(3, (3, 400, 400), shuffle=True, - path_imglist=fname, path_root='', last_batch_handle='pad') + path_imglist=fname, path_root=self.IMAGES_DIR, last_batch_handle='pad') ] _test_imageiter_last_batch(imageiter_list, (2, 3, 400, 400)) def test_det_augmenters(self): # only test if all augmenters will work # TODO(Joshua Zhang): verify the augmenter outputs - im_list = [_generate_objects() + [x] for x in TestImage.IMAGES] - det_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root='', + im_list = [_generate_objects() + [x] for x in self.IMAGES] + det_iter = mx.image.ImageDetIter(2, (3, 300, 300), imglist=im_list, path_root=self.IMAGES_DIR, resize=640, rand_crop=1, rand_pad=1, rand_gray=0.1, rand_mirror=True, mean=True, std=np.array([1.1, 1.03, 1.05]), brightness=0.1, contrast=0.1, saturation=0.1, pca_noise=0.1, hue=0.1, inter_method=10, min_object_covered=0.5, @@ -451,7 +448,3 @@ def test_random_rotate(self): angle_limits) self.assertEqual(out_batch_image.shape, (3, 3, 30, 60)) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_infer_shape.py b/tests/python/unittest/test_infer_shape.py index 1312be0c0081..a2f4cfef3701 100644 --- a/tests/python/unittest/test_infer_shape.py +++ b/tests/python/unittest/test_infer_shape.py @@ -18,7 +18,7 @@ # pylint: skip-file import mxnet as mx from common import models -from nose.tools import * +import pytest def test_mlp2_infer_shape(): # Build MLP @@ -36,7 +36,7 @@ def test_mlp2_infer_shape(): for k, v in true_shapes.items(): assert arg_shape_dict[k] == v -@raises(mx.MXNetError) +@pytest.mark.xfail(raises=mx.MXNetError) def test_mlp2_infer_error(): # Test shape inconsistent case out = models.mlp2() @@ -246,6 +246,3 @@ def test_where_partial_shape(): _, result, _ = where_op.infer_shape_partial(cond=(-1,), x=(2, 2), y=(2, 2)) assert result == [None] -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_infer_type.py b/tests/python/unittest/test_infer_type.py index bad83f3ef01b..286556a006c4 100644 --- a/tests/python/unittest/test_infer_type.py +++ b/tests/python/unittest/test_infer_type.py @@ -20,7 +20,6 @@ import numpy as np from common import models, with_seed from mxnet import autograd -from nose.tools import * from mxnet.test_utils import assert_almost_equal @with_seed() @@ -52,7 +51,3 @@ def test_func(a): test64.backward() assert_almost_equal(data64.grad.asnumpy(), data32.grad.asnumpy(), atol=1e-5, rtol=1e-5) - -if __name__ == '__main__': - import nose - nose.runmodule() \ No newline at end of file diff --git a/tests/python/unittest/test_io.py b/tests/python/unittest/test_io.py index a13addb0adca..7de8498d6db1 100644 --- a/tests/python/unittest/test_io.py +++ b/tests/python/unittest/test_io.py @@ -149,7 +149,7 @@ def _test_last_batch_handle(data, labels=None, is_image=False): batch_count_list = [40, 39, 39] else: batch_count_list = [8, 7, 7] - + for idx in range(len(last_batch_handle_list)): dataiter = mx.io.NDArrayIter( data, labels, 128, False, last_batch_handle=last_batch_handle_list[idx]) @@ -168,7 +168,7 @@ def _test_last_batch_handle(data, labels=None, is_image=False): labelcount[int(label[i])] += 1 else: assert not batch.label, 'label is not empty list' - # keep the last batch of 'pad' to be used later + # keep the last batch of 'pad' to be used later # to test first batch of roll_over in second iteration batch_count += 1 if last_batch_handle_list[idx] == 'pad' and \ @@ -243,7 +243,7 @@ def test_NDArrayIter_h5py(): with h5py.File('ndarraytest.h5') as f: f.create_dataset('data', data=data) f.create_dataset('label', data=labels) - + _test_last_batch_handle(f['data'], f['label']) _test_last_batch_handle(f['data'], []) _test_last_batch_handle(f['data']) @@ -285,7 +285,7 @@ def test_NDArrayIter_csr(): {'data': train_data}, dns, batch_size) except ImportError: pass - + # scipy.sparse.csr_matrix with shuffle csr_iter = iter(mx.io.NDArrayIter({'data': train_data}, dns, batch_size, shuffle=True, last_batch_handle='discard')) @@ -411,16 +411,15 @@ def check_libSVMIter_exception(): def test_DataBatch(): - from nose.tools import ok_ from mxnet.io import DataBatch import re batch = DataBatch(data=[mx.nd.ones((2, 3))]) - ok_(re.match( - 'DataBatch: data shapes: \[\(2L?, 3L?\)\] label shapes: None', str(batch))) + assert re.match( + r'DataBatch: data shapes: \[\(2L?, 3L?\)\] label shapes: None', str(batch)) batch = DataBatch(data=[mx.nd.ones((2, 3)), mx.nd.ones( (7, 8))], label=[mx.nd.ones((4, 5))]) - ok_(re.match( - 'DataBatch: data shapes: \[\(2L?, 3L?\), \(7L?, 8L?\)\] label shapes: \[\(4L?, 5L?\)\]', str(batch))) + assert re.match( + r'DataBatch: data shapes: \[\(2L?, 3L?\), \(7L?, 8L?\)\] label shapes: \[\(4L?, 5L?\)\]', str(batch)) def test_CSVIter(): @@ -462,7 +461,7 @@ def assert_dataiter_items_equals(dataiter1, dataiter2): are the equal. """ for batch1, batch2 in zip_longest(dataiter1, dataiter2): - + # ensure iterators contain the same number of batches # zip_longest will return None if on of the iterators have run out of batches assert batch1 and batch2, 'The iterators do not contain the same number of batches' @@ -533,7 +532,7 @@ def assert_dataiter_items_not_equals(dataiter1, dataiter2): random_h=10, max_shear_ratio=2, seed_aug=seed_aug) - + assert_dataiter_items_equals(dataiter1, dataiter2) # check whether to get different images after change seed_aug @@ -573,7 +572,7 @@ def assert_dataiter_items_not_equals(dataiter1, dataiter2): data_shape=(3, 28, 28), batch_size=3, seed_aug=seed_aug) - + assert_dataiter_items_equals(dataiter1, dataiter2) if __name__ == "__main__": diff --git a/tests/python/unittest/test_kvstore.py b/tests/python/unittest/test_kvstore.py index 28d4ec262c06..ad1fe9259489 100644 --- a/tests/python/unittest/test_kvstore.py +++ b/tests/python/unittest/test_kvstore.py @@ -20,8 +20,9 @@ import numpy as np import unittest from mxnet.test_utils import rand_ndarray, assert_almost_equal -from common import setup_module, with_seed, assertRaises, teardown +from common import setup_module, with_seed, assertRaises, teardown_module from mxnet.base import py_str, MXNetError +import pytest shape = (4, 4) keys = [5, 7, 11] @@ -139,6 +140,7 @@ def check_list_kv_pair(kv, key, stype): check_list_kv_pair(init_kv_with_str(), str_keys, stype) +@pytest.mark.skip(reason='Skipped due to segfault. Tracked in #18098') @with_seed() def test_aggregator(): """aggregate value on muliple devices""" @@ -175,6 +177,7 @@ def check_aggregator(kv, key, key_list, stype): @with_seed() +@pytest.mark.skip(reason='Skipped due to segfault. Tracked in #18098') def test_sparse_aggregator(): """aggregate sparse ndarray on muliple devices""" def check_sparse_aggregator(sparse_pull): @@ -344,6 +347,3 @@ def check_invalid_key_types_list(kv, key): check_invalid_key_types_single(kvs[i], single_keys[1 - i]) check_invalid_key_types_list(kvs[i], list_keys[1 - i]) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_kvstore_custom.py b/tests/python/unittest/test_kvstore_custom.py index 4f1f309d24c1..a8f0869f0236 100644 --- a/tests/python/unittest/test_kvstore_custom.py +++ b/tests/python/unittest/test_kvstore_custom.py @@ -20,7 +20,7 @@ import numpy as np import unittest from mxnet.test_utils import rand_ndarray, assert_almost_equal -from common import setup_module, with_seed, assertRaises, teardown +from common import setup_module, with_seed, assertRaises, teardown_module from mxnet.base import py_str, MXNetError shape = (4, 4) @@ -190,6 +190,3 @@ def check_unsupported_methods(kv): kv = mx.kv.create('teststore') check_unsupported_methods(kv) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_loss.py b/tests/python/unittest/test_loss.py index a1a49c97d7f4..e779fd672701 100644 --- a/tests/python/unittest/test_loss.py +++ b/tests/python/unittest/test_loss.py @@ -19,7 +19,7 @@ import numpy as np from mxnet import gluon, autograd from mxnet.test_utils import assert_almost_equal, default_context -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module import unittest @@ -354,7 +354,7 @@ def test_sdml_loss(): N = 5 # number of samples DIM = 10 # Dimensionality EPOCHS = 20 - + # Generate randomized data and 'positive' samples data = mx.random.uniform(-1, 1, shape=(N, DIM)) pos = data + mx.random.uniform(-0.1, 0.1, shape=(N, DIM)) # correlated paired data @@ -380,7 +380,7 @@ def test_sdml_loss(): # After training euclidean distance between aligned pairs should be lower than all non-aligned pairs avg_loss = loss.sum()/len(loss) assert(avg_loss < 0.05) - + @with_seed() def test_cosine_loss(): #Generating samples @@ -488,7 +488,3 @@ def test_bce_loss_with_pos_weight(): npy_bce_loss = (- label_npy * np.log(prob_npy)*pos_weight_npy - (1 - label_npy) * np.log(1 - prob_npy)).mean(axis=1) assert_almost_equal(mx_bce_loss, npy_bce_loss, rtol=1e-4, atol=1e-5) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_metric.py b/tests/python/unittest/test_metric.py index e7273fba35d5..d1e1c5a35fb3 100644 --- a/tests/python/unittest/test_metric.py +++ b/tests/python/unittest/test_metric.py @@ -407,7 +407,3 @@ def test_single_array_input(): rmse.get() _, rmse_res = rmse.get() np.testing.assert_almost_equal(rmse_res, 0.1) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_metric_perf.py b/tests/python/unittest/test_metric_perf.py index 36cbc685797c..fc0f8da5d451 100644 --- a/tests/python/unittest/test_metric_perf.py +++ b/tests/python/unittest/test_metric_perf.py @@ -118,7 +118,3 @@ def test_metric_performance(): run_metric(k, v[1], (data_size * 128)//(n * c), n, c, pred_ctx, label_ctx, **v[0]) print("{:-^90}".format(''), file=sys.stderr) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_module.py b/tests/python/unittest/test_module.py index b82933126d67..65d86f62baf4 100644 --- a/tests/python/unittest/test_module.py +++ b/tests/python/unittest/test_module.py @@ -22,7 +22,7 @@ import numpy as np from functools import reduce from mxnet.module.executor_group import DataParallelExecutorGroup -from common import setup_module, with_seed, assertRaises, teardown +from common import setup_module, with_seed, assertRaises, teardown_module from collections import namedtuple curr_path = os.path.dirname(os.path.abspath(os.path.expanduser(__file__))) sys.path.insert(0, os.path.join(curr_path, "../train")) @@ -1029,7 +1029,3 @@ def get_module_idx2name(mod): mod2.init_optimizer(optimizer=opt) assert mod2._optimizer.idx2name == get_module_idx2name(mod2) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_ndarray.py b/tests/python/unittest/test_ndarray.py index 961d3c8ba699..f8e89c0e8211 100644 --- a/tests/python/unittest/test_ndarray.py +++ b/tests/python/unittest/test_ndarray.py @@ -23,7 +23,7 @@ import pickle as pkl import random import functools -from nose.tools import assert_raises, raises +import pytest from common import with_seed, assertRaises, TemporaryDirectory from mxnet.test_utils import almost_equal from mxnet.test_utils import assert_almost_equal, assert_exception @@ -1341,7 +1341,7 @@ def check_fluent_regular(func, kwargs, shape=(5, 17, 1), equal_nan=False): check_fluent_regular('squeeze', {'axis': (1, 3)}, shape=(2, 1, 3, 1, 4)) -@raises(ValueError) +@pytest.mark.xfail(raises=ValueError) def test_bool_ambiguous(): bool(mx.nd.ones((2,3,4))) @@ -1603,10 +1603,10 @@ def convert(num): # Test basic indexing with newaxis (None, False), ((1, None, -2, 3, -4), False), - ((1, slice(2, 5), None), False), - ((slice(None), slice(1, 4), None, slice(2, 3)), False), - ((slice(1, 3), slice(1, 3), slice(1, 3), slice(1, 3), None), False), - ((slice(1, 3), slice(1, 3), None, slice(1, 3), slice(1, 3)), False), + ((1, slice(2, 5), None), False), + ((slice(None), slice(1, 4), None, slice(2, 3)), False), + ((slice(1, 3), slice(1, 3), slice(1, 3), slice(1, 3), None), False), + ((slice(1, 3), slice(1, 3), None, slice(1, 3), slice(1, 3)), False), ((None, slice(1, 2), 3, None), False), ((1, None, 2, 3, None, None, 4), False), # Advanced indexing @@ -2061,7 +2061,3 @@ def test_load_saved_gpu_array_when_no_gpus_are_present(): # but there are no GPUs array.__setstate__(ndarray_state) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_numpy_gluon.py b/tests/python/unittest/test_numpy_gluon.py index f3f01fc2ae92..713591795a43 100644 --- a/tests/python/unittest/test_numpy_gluon.py +++ b/tests/python/unittest/test_numpy_gluon.py @@ -431,7 +431,3 @@ def hybrid_forward(self, F, valid_length): assert mx.test_utils.same(out1.asnumpy(), out2.asnumpy()) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_numpy_interoperability.py b/tests/python/unittest/test_numpy_interoperability.py index 919e0dff17b8..824fa1e68300 100644 --- a/tests/python/unittest/test_numpy_interoperability.py +++ b/tests/python/unittest/test_numpy_interoperability.py @@ -1813,7 +1813,7 @@ def test_shapes(): a = np.ones((2,), dtype=dt) b = np.ones((2,), dtype=dt) OpArgMngr.add_workload('matmul', a, b) - + def test_result_types(): mat = np.ones((1,1)) vec = np.ones((1,)) @@ -1822,7 +1822,7 @@ def test_result_types(): v = vec.astype(dt) for arg in [(m, v), (v, m), (m, m)]: OpArgMngr.add_workload('matmul', *arg) - + def test_scalar_output(): vec1 = np.array([2]) vec2 = np.array([3, 4]).reshape(1, -1) @@ -1831,7 +1831,7 @@ def test_scalar_output(): v2 = vec2.astype(dt) OpArgMngr.add_workload('matmul', v1, v2) OpArgMngr.add_workload('matmul', v2.T, v1) - + def test_vector_vector_values(): vec1 = np.array([1, 2]) vec2 = np.array([3, 4]).reshape(-1, 1) @@ -1863,7 +1863,7 @@ def test_matrix_vector_values(): m2 = mat2.astype(dt) OpArgMngr.add_workload('matmul', m1, v) OpArgMngr.add_workload('matmul', m2, v) - + def test_matrix_matrix_values(): mat1 = np.array([[1, 2], [3, 4]]) mat2 = np.array([[1, 0], [1, 1]]) @@ -3265,7 +3265,3 @@ def test_np_fallback_ops(): op_list = np.fallback.__all__ + ['linalg.{}'.format(op_name) for op_name in np.fallback_linalg.__all__] check_interoperability(op_list) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_numpy_ndarray.py b/tests/python/unittest/test_numpy_ndarray.py index 0f57947b6c1f..98267e9bc650 100644 --- a/tests/python/unittest/test_numpy_ndarray.py +++ b/tests/python/unittest/test_numpy_ndarray.py @@ -21,12 +21,13 @@ import itertools import os import unittest +import pytest import numpy as _np import mxnet as mx from mxnet import np, npx, autograd from mxnet.gluon import HybridBlock -from mxnet.test_utils import same, assert_almost_equal, rand_shape_nd, rand_ndarray, retry, use_np -from common import with_seed, TemporaryDirectory +from mxnet.test_utils import same, assert_almost_equal, rand_shape_nd, rand_ndarray, use_np +from common import with_seed, retry, TemporaryDirectory from mxnet.test_utils import verify_generator, gen_buckets_probs_with_ppf, assert_exception, is_op_runnable, collapse_sum_like from mxnet.ndarray.ndarray import py_slice from mxnet.base import integer_types @@ -623,7 +624,7 @@ def test_nd_no_format(): if str(context)[:3] != 'gpu': test_0d() test_nd_format() - test_nd_no_format() + test_nd_no_format() # if the program is running in GPU, the formatted string would be appended with context notation # for exmpale, if a = np.array([np.pi]), the return value of '{}'.format(a) is '[3.1415927] @gpu(0)' @@ -1238,7 +1239,7 @@ def test_boolean_indexing_assign(): mx_mask = np.array([[False,True, True],[False, True,False]],dtype=np.bool) np_mask = mx_mask.asnumpy() - + np_data[0, np_mask] = 5 mx_data[0, mx_mask] = 5 assert_almost_equal(mx_data.asnumpy(), np_data, rtol=1e-3, atol=1e-5, use_broadcast=False) @@ -1316,7 +1317,3 @@ def test_np_ndarray_pickle(): a_load = pickle.load(f) same(a.asnumpy(), a_load.asnumpy()) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_numpy_op.py b/tests/python/unittest/test_numpy_op.py index 1edee775298c..3b11b35742b1 100644 --- a/tests/python/unittest/test_numpy_op.py +++ b/tests/python/unittest/test_numpy_op.py @@ -26,7 +26,7 @@ import mxnet as mx import scipy.stats as ss import scipy.special as scipy_special -from nose.tools import assert_raises +import pytest from mxnet import np, npx from mxnet.gluon import HybridBlock from mxnet.base import MXNetError @@ -34,7 +34,7 @@ from mxnet.test_utils import check_numeric_gradient, use_np, collapse_sum_like from mxnet.test_utils import new_matrix_with_real_eigvals_nd from mxnet.test_utils import new_sym_matrix_with_real_eigvals_nd -from common import assertRaises, with_seed +from common import assertRaises, with_seed, retry import random from mxnet.test_utils import verify_generator, gen_buckets_probs_with_ppf from mxnet.numpy_op_signature import _get_builtin_op @@ -552,7 +552,7 @@ def ShapeReduce(mat, shape, is_b=False): for shape_a, shape_b in bad_shapes: a = np.random.uniform(size=shape_a) b = np.random.uniform(size=shape_b) - assert_raises(MXNetError, lambda: np.matmul(a, b)) + pytest.raises(MXNetError, lambda: np.matmul(a, b)) @with_seed() @@ -1479,7 +1479,7 @@ def gt_grad_batch_dot_numpy(lhs, rhs, ograd, transpose_a, transpose_b, lhs_req, for dtype in dtypes: lhs_val = mx.np.array(_np.random.uniform(-1.0, 1.0, lhs_shape), dtype=dtype) rhs_val = mx.np.array(_np.random.uniform(-1.0, 1.0, rhs_shape), dtype=dtype) - assert_raises(MXNetError, lambda: mx.npx.batch_dot(lhs_val, rhs_val, + pytest.raises(MXNetError, lambda: mx.npx.batch_dot(lhs_val, rhs_val, transpose_a=transpose_a, transpose_b=transpose_b)) @@ -1964,8 +1964,8 @@ def hybrid_forward(self, F, a): assert_almost_equal(mx_out.asnumpy(), np_out, rtol=1e-3, atol=1e-5, use_broadcast=False) # Test for error raising dat = np.random.normal(0, 1, (3, 4, 5), dtype=np.float32) - assert_raises(ValueError, lambda: dat.transpose((0, 0, 1))) - assert_raises(MXNetError, lambda: dat.transpose((0, 1, 3))) + pytest.raises(ValueError, lambda: dat.transpose((0, 0, 1))) + pytest.raises(MXNetError, lambda: dat.transpose((0, 1, 3))) @@ -4490,6 +4490,7 @@ def hybrid_forward(self, F, a): @with_seed() @use_np +@pytest.mark.skip(reason='Skipped as the test is flaky and the feature causes curand error. Tracked in #18100') def test_np_histogram(): shapes = [(), (3, 4), (3, 0)] @@ -4507,6 +4508,7 @@ def test_np_histogram(): @with_seed() @use_np +@pytest.mark.skip(reason='Skipped as the test is flaky and the feature causes curand error. Tracked in #18100') def test_np_choice(): class TestUniformChoice(HybridBlock): def __init__(self, sample_size, replace): @@ -5683,7 +5685,7 @@ class TestLstsq(HybridBlock): def __init__(self, rcond): super(TestLstsq, self).__init__() self._rcond = rcond - + def hybrid_forward(self, F, a, b, rcond='warn'): return F.np.linalg.lstsq(a, b, rcond=self._rcond) @@ -6446,6 +6448,7 @@ def hybrid_forward(self, F, a): @with_seed() @use_np +@pytest.mark.skip(reason='Skipped as the test is flaky and the feature causes curand error. Tracked in #18100') def test_np_full_like(): class TestFullLike(HybridBlock): def __init__(self, fill_value, dtype, ctx): @@ -7080,10 +7083,10 @@ def __init__(self, n, k=0, m=None): if m is None: m = n self._m = m - + def hybrid_forward(self, F, x, *args, **kwargs): return x, F.np.tril_indices(n=self._n, k=self._k, m=self._m) - + for n in _np.random.random_integers(-10, 50, 2): for k in _np.random.random_integers(-50, 50, 2): for m in _np.random.random_integers(-10, 50, 2): @@ -7104,7 +7107,7 @@ def hybrid_forward(self, F, x, *args, **kwargs): np_data[np_out] = -10 mx_data[mx_out] = -10 assert same(np_data, mx_data.asnumpy()) - + @with_seed() @use_np @@ -7443,6 +7446,7 @@ def dbg(name, data): @with_seed() @use_np +@pytest.mark.skip(reason='Skipped as the test is flaky and the feature causes curand error. Tracked in #18100') def test_np_diagflat(): class TestDiagflat(HybridBlock): def __init__(self, k=0): @@ -7818,7 +7822,7 @@ def hybrid_forward(self, F, a): a = np.random.uniform(-1.0, 1.0, size=a_shape) np_out = _np.median(a.asnumpy(), axis=axis, keepdims=keepdims) mx_out = test_median(a) - + assert mx_out.shape == np_out.shape assert_almost_equal(mx_out.asnumpy(), np_out, atol=atol, rtol=rtol) @@ -8834,10 +8838,10 @@ def __init__(self, left=None, right=None, period=None): self._left = left self._right = right self._period = period - + def hybrid_forward(self, F, x, xp, fp): return F.np.interp(x, xp, fp, left=self._left, right=self._right, period=self._period) - + class TestInterpScalar(HybridBlock): def __init__(self, x=None, left=None, right=None, period=None): super(TestInterpScalar, self).__init__() @@ -8845,7 +8849,7 @@ def __init__(self, x=None, left=None, right=None, period=None): self._left = left self._right = right self._period = period - + def hybrid_forward(self, F, xp, fp): return F.np.interp(self._x, xp, fp, left=self._left, right=self._right, period=self._period) @@ -8872,13 +8876,13 @@ def hybrid_forward(self, F, xp, fp): else: x = np.random.uniform(0, 100, size=xshape).astype(xtype) xp = np.sort(np.random.choice(100, dsize, replace=False).astype(dtype)) - fp = np.random.uniform(-50, 50, size=dsize).astype(dtype) + fp = np.random.uniform(-50, 50, size=dsize).astype(dtype) np_x = x.asnumpy() if x_scalar and xshape == (): x = x.item() np_x = x test_interp = TestInterpScalar(x=x, left=left, right=right, period=period) - else: + else: test_interp = TestInterp(left=left, right=right, period=period) if hybridize: test_interp.hybridize() @@ -8944,6 +8948,7 @@ def hybrid_forward(self, F, a, weights): @with_seed() @use_np +@pytest.mark.skip(reason='Test hangs. Tracked in #18144') def test_np_empty_like(): class TestEmptyLike(HybridBlock): def __init__(self, dtype, order, subok): @@ -9268,7 +9273,7 @@ def __init__(self, axis=0, start=0): super(TestRollaxis, self).__init__() self._axis = axis self._start = start - + def hybrid_forward(self, F, a, *args, **kwargs): return F.np.rollaxis(a, axis=self._axis, start=self._start) @@ -9327,7 +9332,3 @@ def hybrid_forward(self, F, a): elif grad_req == 'add': assert_almost_equal(new_grad, old_grad + 1) - -if __name__ == '__main__': - import nose - nose.runmodule() \ No newline at end of file diff --git a/tests/python/unittest/test_operator.py b/tests/python/unittest/test_operator.py index 61e385b3f4f8..4e7c75cde8a4 100644 --- a/tests/python/unittest/test_operator.py +++ b/tests/python/unittest/test_operator.py @@ -29,9 +29,9 @@ from mxnet.test_utils import * from mxnet.operator import * from mxnet.base import py_str, MXNetError, _as_list -from common import setup_module, with_seed, teardown, assert_raises_cudnn_not_satisfied, assert_raises_cuda_not_satisfied, assertRaises +from common import setup_module, with_seed, teardown_module, assert_raises_cudnn_not_satisfied, assert_raises_cuda_not_satisfied, assertRaises from common import run_in_spawned_process -from nose.tools import assert_raises, ok_ +import pytest import unittest import os @@ -6069,7 +6069,7 @@ def f(in_data, out_data): b = mx.nd.zeros((1, 4)) c = mx.nd.Custom(a, b, op_type='Dot1') c.wait_to_read() - assert_raises(MXNetError, custom_exc1) + pytest.raises(MXNetError, custom_exc1) # 2. error in pushing operator to engine def custom_exc2(): @@ -6081,7 +6081,7 @@ def f(in_data, out_data): # trigger error by invalid input shapes of operands c = mx.nd.Custom(a, b, op_type='Dot2') c.wait_to_read() - assert_raises(MXNetError, custom_exc2) + pytest.raises(MXNetError, custom_exc2) # 3. error in real execution if default_context().device_type == 'cpu': @@ -6098,7 +6098,7 @@ def f(in_data, out_data): b = mx.nd.zeros((1, 2)) c = mx.nd.Custom(a, b, op_type='Dot3') c.wait_to_read() - assert_raises(MXNetError, custom_exc3) + pytest.raises(MXNetError, custom_exc3) def custom_exc4(): def f(in_data, out_data): @@ -6112,7 +6112,7 @@ def f(in_data, out_data): b = mx.nd.zeros((1, 2)) c = mx.nd.Custom(a, b, op_type='Dot4') c.wait_to_read() - assert_raises(MXNetError, custom_exc4) + pytest.raises(MXNetError, custom_exc4) @with_seed() @@ -7157,11 +7157,11 @@ def test_dropout_reproducibility(): assert_almost_equal(result1.asnumpy(), result5.asnumpy()) assert_almost_equal(result2.asnumpy(), result6.asnumpy()) - with assert_raises(AssertionError): + with pytest.raises(AssertionError): assert_almost_equal(result1.asnumpy(), result2.asnumpy()) - with assert_raises(AssertionError): + with pytest.raises(AssertionError): assert_almost_equal(result1.asnumpy(), result3.asnumpy()) - with assert_raises(AssertionError): + with pytest.raises(AssertionError): assert_almost_equal(result2.asnumpy(), result4.asnumpy()) @unittest.skip("test fails intermittently. temporarily disabled till it gets fixed. tracked at https://github.com/apache/incubator-mxnet/issues/11290") @@ -7704,8 +7704,8 @@ def max(): a = mx.nd.zeros(shape=(5, 0)) a.max() - assert_raises(MXNetError, min) - assert_raises(MXNetError, max) + pytest.raises(MXNetError, min) + pytest.raises(MXNetError, max) @with_seed() @@ -9343,18 +9343,18 @@ def test_add_n(): def test_get_all_registered_operators(): ops = get_all_registered_operators() - ok_(isinstance(ops, list)) - ok_(len(ops) > 0) - ok_('Activation' in ops) + assert isinstance(ops, list) + assert len(ops) > 0 + assert 'Activation' in ops def test_get_operator_arguments(): operator_arguments = get_operator_arguments('Activation') - ok_(isinstance(operator_arguments, OperatorArguments)) - ok_(operator_arguments.names == ['data', 'act_type']) - ok_(operator_arguments.types - == ['NDArray-or-Symbol', "{'relu', 'sigmoid', 'softrelu', 'softsign', 'tanh'}, required"]) - ok_(operator_arguments.narg == 2) + assert isinstance(operator_arguments, OperatorArguments) + assert operator_arguments.names == ['data', 'act_type'] + assert operator_arguments.types \ + == ['NDArray-or-Symbol', "{'relu', 'sigmoid', 'softrelu', 'softsign', 'tanh'}, required"] + assert operator_arguments.narg == 2 def test_transpose_infer_shape_back(): @@ -10016,6 +10016,3 @@ def test_broadcast_ops_on_misaligned_input_oneside(): mx.nd.waitall() assert_almost_equal(f, expected) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_optimizer.py b/tests/python/unittest/test_optimizer.py old mode 100755 new mode 100644 index d3545ce86638..bf04179774a8 --- a/tests/python/unittest/test_optimizer.py +++ b/tests/python/unittest/test_optimizer.py @@ -22,10 +22,10 @@ import mxnet.lr_scheduler as lr_scheduler from mxnet import gluon import unittest -from nose.tools import raises +import pytest import math from mxnet.test_utils import * -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module @with_seed() def test_learning_rate(): @@ -44,7 +44,7 @@ def test_learning_rate(): assert o3.learning_rate == 1024 -@raises(UserWarning) +@pytest.mark.xfail(raises=UserWarning) @with_seed() def test_learning_rate_expect_user_warning(): lr_s = lr_scheduler.FactorScheduler(step=1) @@ -284,7 +284,7 @@ def test_lars(): def test_lamb(): opt1 = mx.optimizer.LAMB opt2 = mx.optimizer.LAMB - + shapes = [(3, 4, 5), (10, 4), (7,)] beta1_options = [{}, {'beta1': 0.5}] beta2_options = [{}, {'beta2': 0.8}] @@ -953,8 +953,3 @@ def test_cosine_scheduler(): np.testing.assert_almost_equal(cosine_sched(steps), final_lr) assert (cosine_sched(500) > 1.5) - -if __name__ == '__main__': - import nose - nose.runmodule() - diff --git a/tests/python/unittest/test_predictor.py b/tests/python/unittest/test_predictor.py index fc2fbf600cbc..325b830e4226 100644 --- a/tests/python/unittest/test_predictor.py +++ b/tests/python/unittest/test_predictor.py @@ -26,7 +26,7 @@ import mxnet.ndarray as nd from mxnet import gluon from mxnet.test_utils import assert_almost_equal -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module @with_seed() def test_predictor(): @@ -81,7 +81,3 @@ def test_load_ndarray(): for k in nd_data.keys(): assert_almost_equal(nd_data[k].asnumpy(), nd_load[k], rtol=1e-5, atol=1e-6) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_profiler.py b/tests/python/unittest/test_profiler.py index 5a0baca1b684..bf745043e871 100644 --- a/tests/python/unittest/test_profiler.py +++ b/tests/python/unittest/test_profiler.py @@ -263,7 +263,7 @@ def check_sorting(debug_str, sort_by, ascending): for domain_name, domain in target_dict['Time'].items(): lst = [item[sort_by_options[sort_by]] for item_name, item in domain.items()] check_ascending(lst, ascending) - # Memory items do not have stat 'Total' + # Memory items do not have stat 'Total' if sort_by != 'total': for domain_name, domain in target_dict['Memory'].items(): lst = [item[sort_by_options[sort_by]] for item_name, item in domain.items()] @@ -372,7 +372,7 @@ def check_custom_operator_profiling_multiple_custom_ops_output(debug_str): def custom_operator_profiling_multiple_custom_ops(seed, mode, file_name): class MyAdd(mx.operator.CustomOp): - def forward(self, is_train, req, in_data, out_data, aux): + def forward(self, is_train, req, in_data, out_data, aux): self.assign(out_data[0], req[0], in_data[0] + 1) def backward(self, req, out_grad, in_data, out_data, in_grad, aux): @@ -610,7 +610,3 @@ def test_gpu_memory_profiler_gluon(): row['Attribute Name'] == ":": assert False, "Unknown allocation entry has been encountered" - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_random.py b/tests/python/unittest/test_random.py index efcf16dc78da..79fab10c9962 100644 --- a/tests/python/unittest/test_random.py +++ b/tests/python/unittest/test_random.py @@ -19,12 +19,13 @@ import math import itertools import mxnet as mx -from mxnet.test_utils import verify_generator, gen_buckets_probs_with_ppf, retry, assert_almost_equal +from mxnet.test_utils import verify_generator, gen_buckets_probs_with_ppf, assert_almost_equal import numpy as np import random as rnd -from common import setup_module, with_seed, random_seed, teardown +from common import setup_module, with_seed, retry, random_seed, teardown_module import scipy.stats as ss import unittest +import pytest from mxnet.test_utils import * def same(a, b): @@ -339,7 +340,7 @@ def check_with_device(device, dtype): un1 = np.maximum(un1, 1e-1) if name == 'uniform': un1 = np.minimum(np.maximum(un1.reshape((un1.shape[0],un1.shape[1],-1)), p1.reshape((p1.shape[0],p1.shape[1],-1))+1e-4), - p2.reshape((p2.shape[0],p2.shape[1],-1))-1e-4).reshape(un1.shape) + p2.reshape((p2.shape[0],p2.shape[1],-1))-1e-4).reshape(un1.shape) for use_log in [False, True]: test_pdf = symbol(v0, v1, is_log=use_log) if single_param else symbol(v0, v1, v2, is_log=use_log) forw_atol = 1e-7 if dtype != np.float16 else 1e-3 @@ -349,7 +350,7 @@ def check_with_device(device, dtype): if single_param: res = pdffunc(un1.reshape((un1.shape[0],un1.shape[1],-1)), p1.reshape((p1.shape[0],p1.shape[1],-1))).reshape(un1.shape) - if use_log: + if use_log: res = np.log(res) check_symbolic_forward(test_pdf, [un1, p1], [res], atol=forw_atol, rtol=forw_rtol, dtype=dtype) if dtype == np.float64: @@ -558,48 +559,47 @@ def test_parallel_random_seed_setting_for_context(): for i in range(1, len(samples_sym)): assert same(samples_sym[i - 1], samples_sym[i]) -@retry(5) @with_seed() -def test_sample_multinomial(): - for dtype in ['uint8', 'int32', 'float16', 'float32', 'float64']: # output array types - for x in [mx.nd.array([[0,1,2,3,4],[4,3,2,1,0]])/10.0, mx.nd.array([0,1,2,3,4])/10.0]: - dx = mx.nd.ones_like(x) - mx.contrib.autograd.mark_variables([x], [dx]) - # Adding rtol and increasing samples needed to pass with seed 2951820647 - samples = 10000 - with mx.autograd.record(): - y, prob = mx.nd.random.multinomial(x, shape=samples, get_prob=True, dtype=dtype) - r = prob * 5 - r.backward() - - assert(np.dtype(dtype) == y.dtype) - y = y.asnumpy() - x = x.asnumpy() - dx = dx.asnumpy() - if len(x.shape) is 1: - x = x.reshape((1, x.shape[0])) - dx = dx.reshape(1, dx.shape[0]) - y = y.reshape((1, y.shape[0])) - prob = prob.reshape((1, prob.shape[0])) - for i in range(x.shape[0]): - freq = np.bincount(y[i,:].astype('int32'), minlength=5)/np.float32(samples)*x[i,:].sum() - assert_almost_equal(freq, x[i], rtol=0.20, atol=1e-1) - rprob = x[i][y[i].astype('int32')]/x[i].sum() - assert_almost_equal(np.log(rprob), prob.asnumpy()[i], atol=1e-5) - - real_dx = np.zeros((5,)) - for j in range(samples): - real_dx[int(y[i][j])] += 5.0 / rprob[j] - assert_almost_equal(real_dx, dx[i, :], rtol=1e-4, atol=1e-5) - for dtype in ['uint8', 'float16', 'float32']: - # Bound check for the output data types. 'int32' and 'float64' require large memory so are skipped. - x = mx.nd.zeros(2 ** 25) # Larger than the max integer in float32 without precision loss. - bound_check = False - try: - y = mx.nd.random.multinomial(x, dtype=dtype) - except mx.MXNetError as e: - bound_check = True - assert bound_check +@pytest.mark.parametrize('dtype', ['uint8', 'int32', 'float16', 'float32', 'float64']) +@pytest.mark.parametrize('x', [[[0,1,2,3,4],[4,3,2,1,0]], [0,1,2,3,4]]) +def test_sample_multinomial(dtype, x): + x = mx.nd.array(x) / 10.0 + dx = mx.nd.ones_like(x) + mx.contrib.autograd.mark_variables([x], [dx]) + # Adding rtol and increasing samples needed to pass with seed 2951820647 + samples = 10000 + with mx.autograd.record(): + y, prob = mx.nd.random.multinomial(x, shape=samples, get_prob=True, dtype=dtype) + r = prob * 5 + r.backward() + + assert(np.dtype(dtype) == y.dtype) + y = y.asnumpy() + x = x.asnumpy() + dx = dx.asnumpy() + if len(x.shape) is 1: + x = x.reshape((1, x.shape[0])) + dx = dx.reshape(1, dx.shape[0]) + y = y.reshape((1, y.shape[0])) + prob = prob.reshape((1, prob.shape[0])) + for i in range(x.shape[0]): + freq = np.bincount(y[i,:].astype('int32'), minlength=5)/np.float32(samples)*x[i,:].sum() + assert_almost_equal(freq, x[i], rtol=0.20, atol=1e-1) + rprob = x[i][y[i].astype('int32')]/x[i].sum() + assert_almost_equal(np.log(rprob), prob.asnumpy()[i], atol=1e-5) + + real_dx = np.zeros((5,)) + for j in range(samples): + real_dx[int(y[i][j])] += 5.0 / rprob[j] + assert_almost_equal(real_dx, dx[i, :], rtol=1e-4, atol=1e-5) + +@pytest.mark.parametrize('dtype', ['uint8', 'float16', 'float32']) +@with_seed() +@retry(5) +@pytest.mark.xfail(raises=mx.MXNetError) +def test_sample_multinomial_bound_check(dtype): + # Larger than the max integer in float32 without precision loss. + y = mx.nd.random.multinomial(mx.nd.zeros(2 ** 25), dtype=dtype) # Test the generators with the chi-square testing @with_seed() @@ -1035,7 +1035,3 @@ def test_sample_multinomial_num_outputs(): assert isinstance(out, list) assert len(out) == 2 - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_recordio.py b/tests/python/unittest/test_recordio.py index 81561b987839..6db54d541244 100644 --- a/tests/python/unittest/test_recordio.py +++ b/tests/python/unittest/test_recordio.py @@ -22,7 +22,7 @@ import tempfile import random import string -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module @with_seed() def test_recordio(): diff --git a/tests/python/unittest/test_rnn.py b/tests/python/unittest/test_rnn.py index a5588250e515..ab333f93c918 100644 --- a/tests/python/unittest/test_rnn.py +++ b/tests/python/unittest/test_rnn.py @@ -308,7 +308,4 @@ def test_encode_sentences(): print(result, vocab) assert vocab == {'a': 1, 'b': 2, 'c': 3, 'UNK': 0} assert result == [[1,2,3],[2,3,0]] - -if __name__ == '__main__': - import nose - nose.runmodule() + diff --git a/tests/python/unittest/test_runtime.py b/tests/python/unittest/test_runtime.py index 82e2314532b8..0bd4d4c4dcb1 100644 --- a/tests/python/unittest/test_runtime.py +++ b/tests/python/unittest/test_runtime.py @@ -19,14 +19,14 @@ import sys from mxnet.runtime import * from mxnet.base import MXNetError -from nose.tools import * +import pytest def test_features(): features = Features() print(features) - ok_('CUDA' in features) - ok_(len(features) >= 30) + assert 'CUDA' in features + assert len(features) >= 30 def test_is_singleton(): @@ -39,17 +39,13 @@ def test_is_enabled(): features = Features() for f in features: if features[f].enabled: - ok_(features.is_enabled(f)) + assert features.is_enabled(f) else: - ok_(not features.is_enabled(f)) + assert not features.is_enabled(f) -@raises(RuntimeError) +@pytest.mark.xfail(raises=RuntimeError) def test_is_enabled_not_existing(): features = Features() features.is_enabled('this girl is on fire') - -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_sparse_ndarray.py b/tests/python/unittest/test_sparse_ndarray.py index 9a1fce4ff197..de06c7be0777 100644 --- a/tests/python/unittest/test_sparse_ndarray.py +++ b/tests/python/unittest/test_sparse_ndarray.py @@ -19,7 +19,7 @@ from mxnet.ndarray import NDArray from mxnet.test_utils import * -from common import setup_module, with_seed, random_seed, teardown +from common import setup_module, with_seed, random_seed, teardown_module from mxnet.base import mx_real_t from numpy.testing import assert_allclose import numpy.random as rnd @@ -1056,6 +1056,3 @@ def check_sparse_getnnz(density, axis): for a in axis: check_sparse_getnnz(d, a) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_sparse_operator.py b/tests/python/unittest/test_sparse_operator.py index 4c4e3dbdfc51..f23f59414816 100644 --- a/tests/python/unittest/test_sparse_operator.py +++ b/tests/python/unittest/test_sparse_operator.py @@ -17,7 +17,7 @@ from mxnet.test_utils import * from mxnet.base import MXNetError -from common import setup_module, with_seed, teardown, assertRaises +from common import setup_module, with_seed, teardown_module, assertRaises import random import warnings @@ -2346,6 +2346,3 @@ def test_reshape_backward_fallback(): assert_almost_equal(grad_w_nd.asnumpy(), expected_grad_nd) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_subgraph.py b/tests/python/unittest/test_subgraph.py index 3da125a946bc..b1a7aa3f3abb 100644 --- a/tests/python/unittest/test_subgraph.py +++ b/tests/python/unittest/test_subgraph.py @@ -21,7 +21,7 @@ import mxnet as mx import copy from mxnet.test_utils import * -from common import setup_module, with_seed, teardown +from common import setup_module, with_seed, teardown_module from mxnet.gluon.model_zoo.vision import get_model def make_subgraph(subg, *args): @@ -190,6 +190,3 @@ def create_operator(self, ctx, shapes, dtypes): c.bind(mx.cpu(), {'a': inp}).forward() mx.nd.waitall() -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_subgraph_op.py b/tests/python/unittest/test_subgraph_op.py index e414a9836ccb..bffb38e6dd5d 100644 --- a/tests/python/unittest/test_subgraph_op.py +++ b/tests/python/unittest/test_subgraph_op.py @@ -41,7 +41,7 @@ def network_structure_2(): ret1 = mx.sym.cos(ret) ret2 = mx.sym.sin(ret) ret = ret1 + ret2 - return (ret, ['data'], [(2, 3, 10, 10)]) + return (ret, ['data'], [(2, 3, 10, 10)]) def network_structure_3(): # this tests whether the partitioned sym can distinguish in_args and aux_states @@ -74,7 +74,7 @@ def network_structure_6(): data3 = mx.sym.sin(data2) conv = mx.sym.Convolution(data=data1, weight=data3, kernel=(2, 2), num_filter=1) return (conv, ['data1'], [(3, 3, 10, 10)]) - + def network_structure_7(): # in this graph, the subgraph node and the other two external nodes form a cycle data = mx.sym.Variable('data', shape=(1,)) @@ -85,7 +85,7 @@ def network_structure_7(): ret = ret1 + ret2 return (ret, ['data'], [(1,)]) -def get_graphs(): +def get_graphs(): return [ (network_structure_1(), ['Convolution']), (network_structure_2(), ['exp', 'sin', '_Plus', 'elemwise_add', '_plus']), @@ -271,7 +271,7 @@ def check_subgraph_exe5(sym, subgraph_backend, op_names): assert_almost_equal((outputs1[i] - outputs2[i]).abs().sum().asnumpy(), np.zeros(shape=(1,))) def check_subgraph_exe6(sym, subgraph_backend, op_names): - """Call optimize_for to trigger graph partitioning with shapes/types, then simple_bind + """Call optimize_for to trigger graph partitioning with shapes/types, then simple_bind and compare results of the partitioned sym and the original sym.""" # simple_bind exe1 = sym.simple_bind(ctx=mx.current_context(), grad_req='null') @@ -340,17 +340,17 @@ def check_subgraph_exe8(sym, subgraph_backend, op_names): exe2 = part_sym.bind(ctx=mx.current_context(), args=arg_array, aux_states=aux_array, grad_req='null') exe2.forward() - + # compare outputs outputs1 = exe1.outputs outputs2 = exe2.outputs assert len(outputs1) == len(outputs2) for i in range(len(outputs1)): assert_almost_equal((outputs1[i] - outputs2[i]).abs().sum().asnumpy(), np.zeros(shape=(1,))) - + def check_subgraph_exe9(sym, subgraph_backend, op_names): - """Call hybridize() to partition the graph, and then compare results of the partitioned - sym and the original sym. Here do an inference before hybridizing with the subgraph_backend + """Call hybridize() to partition the graph, and then compare results of the partitioned + sym and the original sym. Here do an inference before hybridizing with the subgraph_backend which means we'll pass shapes/types""" # create Gluon block for given symbol inputs = [mx.sym.var(i, dtype=mx_real_t) for i in sym[1]] @@ -487,6 +487,3 @@ def hybrid_forward(self, F, x): for i in range(len(outputs1)): assert_almost_equal((outputs1[i] - outputs2[i]).abs().sum().asnumpy(), np.zeros(shape=(1,))) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_symbol.py b/tests/python/unittest/test_symbol.py index c913f5c07c9f..7582661741d3 100644 --- a/tests/python/unittest/test_symbol.py +++ b/tests/python/unittest/test_symbol.py @@ -316,14 +316,14 @@ def test_zero_prop(): data = data * data exe = data.simple_bind(ctx=mx.cpu(), data=(10, 3, 256, 256)) - big = int(re.search('Total (\d+) MB allocated', exe.debug_str()).group(1)) + big = int(re.search(r'Total (\d+) MB allocated', exe.debug_str()).group(1)) exe = data.simple_bind(ctx=mx.cpu(), data=(10, 3, 256, 256), grad_req='null') - small1 = int(re.search('Total (\d+) MB allocated', exe.debug_str()).group(1)) + small1 = int(re.search(r'Total (\d+) MB allocated', exe.debug_str()).group(1)) data = mx.sym.stop_gradient(data) exe = data.simple_bind(ctx=mx.cpu(), data=(10, 3, 256, 256)) - small2 = int(re.search('Total (\d+) MB allocated', exe.debug_str()).group(1)) + small2 = int(re.search(r'Total (\d+) MB allocated', exe.debug_str()).group(1)) assert big > small2 assert small1 == small2 @@ -351,7 +351,7 @@ def test_zero_prop2(): def test_simple_bind_incomplete_shape_inference_in_one_forward_pass(): - """This is a special case that results in shape inference + r"""This is a special case that results in shape inference failure after moving simple_bind logic from frontend to backend. Added here for testing against the network similar to the following one. @@ -559,6 +559,3 @@ def test_infershape_happens_for_all_ops_in_graph(): assert False -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_test_utils.py b/tests/python/unittest/test_test_utils.py index 49f0b932fdd5..98e7d94ff793 100644 --- a/tests/python/unittest/test_test_utils.py +++ b/tests/python/unittest/test_test_utils.py @@ -19,10 +19,11 @@ import tempfile import mxnet as mx -from nose.tools import * +import pytest -@raises(Exception) + +@pytest.mark.xfail(raises=Exception) def test_download_retries(): mx.test_utils.download("http://doesnotexist.notfound") @@ -31,4 +32,4 @@ def test_download_successful(): tmpfile = os.path.join(tmp, 'README.md') mx.test_utils.download("https://raw.githubusercontent.com/apache/incubator-mxnet/master/README.md", fname=tmpfile) - assert os.path.getsize(tmpfile) > 100 \ No newline at end of file + assert os.path.getsize(tmpfile) > 100 diff --git a/tests/python/unittest/test_thread_local.py b/tests/python/unittest/test_thread_local.py index 63d97f17ebba..7e875c8fb835 100644 --- a/tests/python/unittest/test_thread_local.py +++ b/tests/python/unittest/test_thread_local.py @@ -221,7 +221,3 @@ def f(): finally: set_np_shape(0) - -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_tvm_op.py b/tests/python/unittest/test_tvm_op.py index e325edcf4d75..55bb7cc2bd92 100644 --- a/tests/python/unittest/test_tvm_op.py +++ b/tests/python/unittest/test_tvm_op.py @@ -67,6 +67,3 @@ def test_tvm_broadcast_add(): assert same(a.grad.asnumpy(), expected_grad_a) assert same(b.grad.asnumpy(), expected_grad_b) -if __name__ == '__main__': - import nose - nose.runmodule() diff --git a/tests/python/unittest/test_viz.py b/tests/python/unittest/test_viz.py index 13210993014a..5c9b78a017d2 100644 --- a/tests/python/unittest/test_viz.py +++ b/tests/python/unittest/test_viz.py @@ -62,6 +62,3 @@ def test_plot_network(): assert "There are multiple variables with the same name in your graph" in str(w[-1].message) assert "fc" in str(w[-1].message) -if __name__ == "__main__": - import nose - nose.runmodule() diff --git a/tests/requirements.txt b/tests/requirements.txt deleted file mode 100644 index e16b764d2746..000000000000 --- a/tests/requirements.txt +++ /dev/null @@ -1,8 +0,0 @@ -# Requirements for tests, those are installed before running on the virtualenv -# Requirements for tests run within the qemu requirement see ci/qemu/test_requirements.txt -mock -nose -nose-timer -ipython -numpy -scipy diff --git a/tools/caffe_converter/test_converter.py b/tools/caffe_converter/test_converter.py old mode 100755 new mode 100644 diff --git a/tools/dependencies/README.md b/tools/dependencies/README.md index c45f33328bbc..5cd4efd72064 100644 --- a/tools/dependencies/README.md +++ b/tools/dependencies/README.md @@ -204,7 +204,7 @@ pip install -e python export NCCL_DEBUG=VERSION vim tests/python/gpu/test_nccl.py # Remove @unittest.skip("Test requires NCCL library installed and enabled during build") then run -nosetests --verbose tests/python/gpu/test_nccl.py +pytest --verbose tests/python/gpu/test_nccl.py # test_nccl.test_nccl_pushpull ... NCCL version 2.4.2+cuda10.0 # ok # ---------------------------------------------------------------------- diff --git a/tools/diagnose.py b/tools/diagnose.py old mode 100755 new mode 100644 diff --git a/tools/flakiness_checker.py b/tools/flakiness_checker.py index 79fa3b1854f0..85eae14c9557 100644 --- a/tools/flakiness_checker.py +++ b/tools/flakiness_checker.py @@ -39,7 +39,7 @@ def run_test_trials(args): new_env = os.environ.copy() new_env["MXNET_TEST_COUNT"] = str(args.num_trials) - + if args.seed is None: logging.info("No test seed provided, using random seed") else: @@ -47,17 +47,17 @@ def run_test_trials(args): verbosity = "--verbosity=" + str(args.verbosity) - code = subprocess.call(["nosetests", verbosity, test_path], + code = subprocess.call(["pytest", verbosity, test_path], env = new_env) - - logging.info("Nosetests terminated with exit code %d", code) + + logging.info("Test terminated with exit code %d", code) def find_test_path(test_file): """Searches for the test file and returns the path if found As a default, the currend working directory is the top of the search. If a directory was provided as part of the argument, the directory will be joined with cwd unless it was an absolute path, in which case, the - absolute path will be used instead. + absolute path will be used instead. """ test_file += ".py" test_path = os.path.split(test_file) @@ -66,7 +66,7 @@ def find_test_path(test_file): for (path, dirs, files) in os.walk(top): if test_path[1] in files: return os.path.join(path, test_path[1]) - raise FileNotFoundError("Could not find " + test_path[1] + + raise FileNotFoundError("Could not find " + test_path[1] + "in directory: " + top) class NameAction(argparse.Action): @@ -82,12 +82,12 @@ def __call__(self, parser, namespace, values, option_string=None): def parse_args(): parser = argparse.ArgumentParser(description="Check test for flakiness") - + parser.add_argument("test", action=NameAction, help="file name and and function name of test, " "provided in the format: . " "or /:") - + parser.add_argument("-n", "--num-trials", metavar="N", default=DEFAULT_NUM_TRIALS, type=int, help="number of test trials, passed as " @@ -95,11 +95,11 @@ def parse_args(): parser.add_argument("-s", "--seed", type=int, help="test seed, passed as MXNET_TEST_SEED, " - "defaults to random seed") + "defaults to random seed") parser.add_argument("-v", "--verbosity", default=DEFAULT_VERBOSITY, type=int, - help="logging level, passed to nosetests") + help="logging level, passed to pytest") args = parser.parse_args() diff --git a/tools/im2rec.py b/tools/im2rec.py old mode 100755 new mode 100644 diff --git a/tools/ipynb2md.py b/tools/ipynb2md.py old mode 100755 new mode 100644 diff --git a/tools/launch.py b/tools/launch.py old mode 100755 new mode 100644 diff --git a/tools/parse_log.py b/tools/parse_log.py old mode 100755 new mode 100644