diff --git a/.gitlab-ci.yml b/.gitlab-ci.yml
new file mode 100644
index 0000000000000000000000000000000000000000..05aa82e59d382052077f2aaa3287e6ae030af7e2
--- /dev/null
+++ b/.gitlab-ci.yml
@@ -0,0 +1,111 @@
+stages:
+  - format
+  - build
+  - lint
+  - test
+  - release
+
+variables:
+  # Package version can only contain numbers (0-9), and dots (.).
+  # Must be in the format of X.Y.Z, i.e. should match /\A\d+\.\d+\.\d+\z/ regular expresion.
+  # See https://docs.gitlab.com/ee/user/packages/generic_packages/#publish-a-package-file
+  PACKAGE_VERSION: "${CI_COMMIT_TAG}"
+  LINUX_AMD64_BINARY: "nm-reactor-linux-amd64-${PACKAGE_VERSION}"
+  PACKAGE_REGISTRY_URL: "${CI_API_V4_URL}/projects/${CI_PROJECT_ID}/packages/generic/nm-reactor/${PACKAGE_VERSION}"
+
+
+.rust_template: &rust_template
+  before_script:
+    - export CARGO_HOME="$CI_PROJECT_DIR/cargo"
+    - rustup --version
+    - rustc --version
+    - cargo --version
+
+rust-nightly:
+  stage: build
+  image: rustlang/rust:nightly
+  needs: []
+  cache:
+    key: "$CI_COMMIT_REF_SLUG"
+    paths:
+      - cargo/
+      - target/
+  <<: *rust_template
+  script:
+    - cargo build --release --verbose
+  artifacts:
+    paths:
+      - target/release/nm-reactor
+
+rust-nightly-test:
+  stage: test
+  image: rustlang/rust:nightly
+  needs:
+    - rust-nightly
+  cache:
+    key: "$CI_COMMIT_REF_SLUG"
+    paths:
+      - cargo/
+      - target/
+    policy: pull
+  <<: *rust_template
+  script:
+    - cargo test --verbose -j 1
+
+rust-nightly-fmt:
+  stage: format
+  image: rustlang/rust:nightly
+  needs: []
+  cache:
+    key: "$CI_COMMIT_REF_SLUG"
+    paths:
+      - cargo/
+      - target/
+    policy: pull
+  <<: *rust_template
+  script:
+    - cargo fmt --all --verbose -- --check
+
+rust-nightly-clippy:
+  stage: lint
+  image: rustlang/rust:nightly
+  needs:
+    - rust-nightly
+  cache:
+    key: "$CI_COMMIT_REF_SLUG"
+    paths:
+      - cargo/
+      - target/
+  <<: *rust_template
+  script:
+    - cargo clippy --all --verbose -- -D warnings
+
+upload:
+  stage: release
+  rules:
+    - if: '$CI_COMMIT_TAG =~ /^\d+\.\d+\.\d+$/'
+  needs:
+    - job: rust-nightly
+      artifacts: true
+  image: curlimages/curl:latest
+  script:
+    - |
+      curl --header "JOB-TOKEN: ${CI_JOB_TOKEN}" --upload-file target/release/nm-reactor ${PACKAGE_REGISTRY_URL}/${LINUX_AMD64_BINARY}
+
+release:
+  stage: release
+  rules:
+    - if: '$CI_COMMIT_TAG =~ /^\d+\.\d+\.\d+$/'
+  needs:
+    - upload
+  image: registry.gitlab.com/gitlab-org/release-cli:latest
+  script:
+    - echo 'Running release_job'
+  release:
+    name: 'v$CI_COMMIT_TAG'
+    description: 'Created using the release-cli'
+    tag_name: '$CI_COMMIT_TAG'
+    assets:
+      links:
+        - name: 'Linux (amd64)'
+          url: "${PACKAGE_REGISTRY_URL}/${DARWIN_AMD64_BINARY}"
\ No newline at end of file