Skip to content
This repository was archived by the owner on Sep 26, 2022. It is now read-only.
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
21 commits
Select commit Hold shift + click to select a range
83918ff
#1: Added initial implementation.
AnastasiiaSergienko Oct 26, 2020
79c010c
#1: Added initial implementation.
AnastasiiaSergienko Oct 26, 2020
13d1dda
#1: Added workflows
AnastasiiaSergienko Oct 26, 2020
67cafd4
#1: Removed test workflow
AnastasiiaSergienko Oct 26, 2020
0f3c714
#1: Added a draft for integration test
AnastasiiaSergienko Nov 6, 2020
e58d32c
#1: Fixed the integration test
AnastasiiaSergienko Nov 9, 2020
81acbd4
#1: Renamed modules
AnastasiiaSergienko Nov 9, 2020
9d3f8df
#1: Added __init__.py
AnastasiiaSergienko Nov 9, 2020
096d212
#1: Fixed a typo in the integration test
AnastasiiaSergienko Nov 9, 2020
024d718
#1: Fixed SELECT query
AnastasiiaSergienko Nov 9, 2020
ba15016
Fix indention and escaping error in test_github_release_file_bucketfs…
tkilias Nov 9, 2020
1e9721d
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
8d1a6dc
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
71e89df
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
440de21
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
b88f4bc
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
2b005a7
#1: Adjusted an integration test
AnastasiiaSergienko Nov 10, 2020
30f9f4b
#1: Fixed review findings
AnastasiiaSergienko Nov 11, 2020
c44c7ff
Update .github/workflows/pytest.yaml
AnastasiiaSergienko Nov 11, 2020
a1a152c
#1: Fixed review findings
AnastasiiaSergienko Nov 11, 2020
e0191e4
Merged coflicts
AnastasiiaSergienko Nov 11, 2020
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
28 changes: 28 additions & 0 deletions .github/workflows/check_setup_py.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,28 @@
name: Check if setup.py is up to date

on: [push, pull_request]

jobs:
check_setup_py:
strategy:
fail-fast: false
matrix:
python-version: [3.6, 3.7]
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v2
- uses: actions/setup-python@v2
with:
python-version: ${{ matrix.python-version }}
- name: Run convert
uses: dephell/dephell_action@master
with:
dephell-env: convert
- name: Show changes on working copy
run: git status --porcelain=v1 -uno
- name: Show diff on working copy
run: git diff
- name: Check if setup.py changed
run: |
[ -z "$(git status --porcelain=v1 -uno 2>/dev/null)" ]
32 changes: 32 additions & 0 deletions .github/workflows/pytest.yaml
Original file line number Diff line number Diff line change
@@ -0,0 +1,32 @@
name: Run pytest tests

on: [ push, pull_request ]

jobs:
integration_tests:
strategy:
fail-fast: false
matrix:
python-version: [3.6, 3.7, 3.8]
runs-on: ubuntu-latest

steps:
- uses: actions/checkout@v2
- uses: actions/setup-python@v2
with:
python-version: ${{ matrix.python-version }}
- uses: abatilo/actions-poetry@v2.0.0
- name: Poetry install
run: poetry install
- name: Poetry build
run: poetry build

- name: Checkout test environment
run: git clone https://github.com/exasol/integration-test-docker-environment.git
working-directory: ..
- name: Spawn EXASOL environemnt
run: ./start-test-env spawn-test-environment --environment-name test --database-port-forward 8888 --bucketfs-port-forward 6666 --db-mem-size 4GB
working-directory: ../integration-test-docker-environment

- name: Poetry run pytest integration tests
run: poetry run pytest tests
135 changes: 135 additions & 0 deletions .gitignore
Original file line number Diff line number Diff line change
@@ -0,0 +1,135 @@
# Byte-compiled / optimized / DLL files
__pycache__/
*.py[cod]
*$py.class

# C extensions
*.so

# Distribution / packaging
.Python
build/
develop-eggs/
dist/
downloads/
eggs/
.eggs/
lib/
lib64/
parts/
sdist/
var/
wheels/
pip-wheel-metadata/
share/python-wheels/
*.egg-info/
.installed.cfg
*.egg
MANIFEST

# PyInstaller
# Usually these files are written by a python script from a template
# before PyInstaller builds the exe, so as to inject date/other infos into it.
*.manifest
*.spec

# Installer logs
pip-log.txt
pip-delete-this-directory.txt

# Unit test / coverage reports
htmlcov/
.tox/
.nox/
.coverage
.coverage.*
.cache
nosetests.xml
coverage.xml
*.cover
*.py,cover
.hypothesis/
.pytest_cache/

# Translations
*.mo
*.pot

# Django stuff:
*.log
local_settings.py
db.sqlite3
db.sqlite3-journal

# Flask stuff:
instance/
.webassets-cache

# Scrapy stuff:
.scrapy

# Sphinx documentation
docs/_build/

# PyBuilder
target/

# Jupyter Notebook
.ipynb_checkpoints

# IPython
profile_default/
ipython_config.py

# pyenv
.python-version

# pipenv
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
# However, in case of collaboration, if having platform-specific dependencies or dependencies
# having no cross-platform support, pipenv may install dependencies that don't work, or not
# install all needed dependencies.
#Pipfile.lock

# PEP 582; used by e.g. github.com/David-OConnor/pyflow
__pypackages__/

# Celery stuff
celerybeat-schedule
celerybeat.pid

# SageMath parsed files
*.sage.py

# Environments
.env
.venv
env/
venv/
ENV/
env.bak/
venv.bak/

# Spyder project settings
.spyderproject
.spyproject

# Rope project settings
.ropeproject

# mkdocs documentation
/site

# mypy
.mypy_cache/
.dmypy.json
dmypy.json

# Pyre type checker
.pyre/

# Poetry
poetry.lock

# PyCharm
.idea
54 changes: 54 additions & 0 deletions README.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,54 @@
# BucketFS Utils Python

This project provides a python library for the Exasol BucketFS system.

Features:

* [Uploading a GitHub release to a bucket](#uploading-github-release-to-bucket)

## How to Use It

Install the package from Github via `pip`:

```
pip install -e git://github.com/exasol/bucketfs-utils-python.git@{ tag name }#egg=exasol-bucketfs-utils-python
```

## Uploading GitHub Release to Bucket

Example:

```python
from exasol_bucketfs_utils_python.github_release_file_bucketfs_uploader import GithubReleaseFileBucketFSUploader

release_uploader = \
GithubReleaseFileBucketFSUploader(file_to_download_name="file",
github_user="user",
repository_name="repository",
release_name="latest",
path_inside_bucket="some/path/")
release_uploader.upload("http://<host>:<port>/<bucket>/", "user", "password")
```

### Run Time Dependencies

| Dependency | Purpose | License |
|-------------------------------|----------------------------------|--------------------|
| [Python 3][python] | Python version 3.6.1 and above | PSF |
| [Requests][requests] | Allows to send HTTP/1.1 requests | Apache License 2.0 |


### Test Dependencies

| Dependency | Purpose | License |
|-------------------------------|-----------------------------------|-------------------|
| [Pytest][pytest] | Testing framework | MIT |
| [Pytest Coverage][pytest-cov] | Tests coverage | MIT |



[python]: https://docs.python.org
[requests]: https://pypi.org/project/requests/

[pytest]: https://docs.pytest.org/en/stable/
[pytest-cov]: https://pypi.org/project/pytest-cov/
3 changes: 3 additions & 0 deletions doc/changes/changelog.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,3 @@
# Changelog

* [0.1.0](changes_0.1.0.md)
7 changes: 7 additions & 0 deletions doc/changes/changes_0.1.0.md
Original file line number Diff line number Diff line change
@@ -0,0 +1,7 @@
# BucketFS Utils Python 0.1.0, released 2020-11-??

Code name: Initial implementation

## Features

#1: Added initial implementation.
Empty file.
Original file line number Diff line number Diff line change
@@ -0,0 +1,41 @@
import requests
from requests.auth import HTTPBasicAuth

from exasol_bucketfs_utils_python.release_link_extractor import ReleaseLinkExtractor


class GithubReleaseFileBucketFSUploader:
def __init__(self, file_to_download_name, github_user, repository_name, release_name, path_inside_bucket):
self.file_to_download_name = file_to_download_name
self.github_user = github_user
self.repository_name = repository_name
self.release_name = release_name
self.path_inside_bucket = path_inside_bucket

def upload(self, address, username, password):
"""
This method uploads the GitHub release into a selected Exasol bucket.
:param address: address in the format 'http://<host>:<port>/<bucket name>'
:param username: bucket writing username
:param password: bucket writing password
"""
download_url = self.__extract_download_url()
r_download = requests.get(download_url, stream=True)
upload_url = self.__build_upload_url(address)
requests.put(upload_url, data=r_download.iter_content(10 * 1024), auth=HTTPBasicAuth(username, password))

def __build_upload_url(self, address):
if self.path_inside_bucket:
address += self.path_inside_bucket
address += self.file_to_download_name
return address

def __extract_download_url(self):
github_api_link = self.__build_github_api_link()
release_link_extractor = ReleaseLinkExtractor(github_api_link)
download_url = release_link_extractor.get_link_by_release_name(self.file_to_download_name)
return download_url

def __build_github_api_link(self):
return "https://api.github.com/repos/{github_user}/{repository_name}/releases/{release_name}".format(
github_user=self.github_user, repository_name=self.repository_name, release_name=self.release_name)
31 changes: 31 additions & 0 deletions exasol_bucketfs_utils_python/release_link_extractor.py
Original file line number Diff line number Diff line change
@@ -0,0 +1,31 @@
import requests


class ReleaseLinkExtractor:
def __init__(self, repository_api_link):
"""
Create a new instance of ReleaseLinkExtractor class.
:param repository_api_link: Link to the GitHub API page with the latest release.
"""
self.repository_api_link = repository_api_link

def get_link_by_release_name(self, file_to_download_name):
"""
This method extracts a link from the GitHub API page searching by a release name.
:param file_to_download_name: the name of the file
:return: a link in a string format
"""
response = requests.get(self.repository_api_link)
json_release_page = response.json()
list_of_available_releases = json_release_page["assets"]
result_link = self.__find_link(list_of_available_releases, file_to_download_name)
if result_link is not None:
return result_link
else:
raise ValueError(
'Release with the name ' + file_to_download_name + ' was not found. Please check the name or select another release')

def __find_link(self, list_of_available_releases, release_name):
for release in list_of_available_releases:
if release_name in release["name"]:
return release["browser_download_url"]
49 changes: 49 additions & 0 deletions githooks/install.sh
Original file line number Diff line number Diff line change
@@ -0,0 +1,49 @@
#!/bin/bash
set -o errexit
set -o nounset
set -o pipefail

SCRIPT_DIR="$(dirname "$(readlink -f "${BASH_SOURCE[0]}")")"
REPO_DIR=$(git rev-parse --show-toplevel)
REPO_DIR="$(readlink -f "${REPO_DIR}")"
GIT_DIR="$REPO_DIR/.git"
GIT_DIR="$(readlink -f "${GIT_DIR}")"

if [[ ! -d "$GIT_DIR" ]]; then
if [[ -d "$REPO_DIR/../.git" ]]; then
GIT_DIR="$REPO_DIR/../.git"
GITHOOKS_PATH="$GIT_DIR/modules/bucketfs-utils-python/hooks"
else
echo "$GIT_DIR is not a git directory." >&2
exit 1
fi
else
GITHOOKS_PATH="$GIT_DIR/hooks"
fi

GITHOOKS_PATH="$(readlink -f "${GITHOOKS_PATH}")"

copy_hook() {
local SCRIPT_PATH="$SCRIPT_DIR/$1"
local GITHOOK_PATH="$GITHOOKS_PATH/$2"
local RELATIVE_PATH=$(realpath --relative-to="$GITHOOKS_PATH" "$SCRIPT_PATH")
pushd "$GITHOOKS_PATH" > /dev/null
if [ -e "$GITHOOK_PATH" ] || [ -L "$GITHOOK_PATH" ]
then
echo
echo "Going to delete old hook $GITHOOK_PATH"
rm "$GITHOOK_PATH" > /dev/null
fi
echo
echo "Link hook to script" >&2
echo "Hook-Path: $GITHOOK_PATH" >&2
echo "Script-path: $SCRIPT_PATH" >&2
echo
ln -s "$RELATIVE_PATH" "$2" > /dev/null
chmod +x "$SCRIPT_PATH" > /dev/null
popd > /dev/null
}

copy_hook pre-commit pre-commit
copy_hook pre-commit post-rewrite
copy_hook pre-push pre-push
Loading