Skip to content

Commit

Permalink
Feature/inplace (#36)
Browse files Browse the repository at this point in the history
* add `inplace` flag to CLI

* inplace flag added to function signatures + docstring updated

* `inplace` testcases added + tiny refactorings

* CHANGELOG.md updated

* `inplace` CLI testcases added

* add `in_place` in readme + it's examples

* `CHANGELOG.md` updated

* `README.md` updated

* help param of `--inplace` updated

* docstring of `in_place` param updated
  • Loading branch information
AHReccese authored Aug 12, 2024
1 parent aaa38a4 commit 787d254
Show file tree
Hide file tree
Showing 6 changed files with 95 additions and 37 deletions.
6 changes: 5 additions & 1 deletion .github/workflows/test.yml
Original file line number Diff line number Diff line change
Expand Up @@ -34,21 +34,25 @@ jobs:
- name: CLI Tests - Clear single .docx file
run: |
dmeta --clear "tests/test_a.docx"
dmeta --clear "tests/test_a.docx" --inplace
ls ./tests
- name: CLI Tests - Clear all .docx files
run: |
cd ./tests
dmeta --clear-all
dmeta --clear-all
dmeta --clear-all --inplace
ls .
cd -
- name: CLI Tests - Update single .docx file
run: |
dmeta --update "tests/test_a.docx" --config "tests/config.json"
dmeta --update "tests/test_a.docx" --config "tests/config.json" --inplace
ls ./tests
- name: CLI Tests - Update all .docx files
run: |
cd ./tests
dmeta --update-all --config "./config.json"
dmeta --update-all --config "./config.json" --inplace
ls .
cd -
- name: Test requirements Installation
Expand Down
6 changes: 6 additions & 0 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,12 @@ and this project adheres to [Semantic Versioning](http://semver.org/spec/v2.0.0.
- `pptx` and `xlsx` support
- `get_microsoft_format` function in `util.py`
- `SECURITY.md`
- `inplace` parameter in the `clear` function in `functions.py`
- `inplace` parameter in the `clear_all` function in `functions.py`
- `inplace` parameter in the `update` function in `functions.py`
- `inplace` parameter in the `update_all` function in `functions.py`
- `inplace` parameter in CLI
- `inplace` tests
### Changed
- `run_dmeta` in `functions.py`
- `read_json` in `util.py`
Expand Down
31 changes: 19 additions & 12 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -62,30 +62,33 @@ DMeta is an open source Python package that removes metadata of Microsoft Office

## Usage
### In Python
#### Clear metadata for a .docx file
⚠️ Use `in_place` to apply the changes directly to the original file.

⚠️`in_place` flag is `False` by default.

#### Clear metadata for a .docx file in place
```python
import os
from dmeta.functions import clear

DOCX_FILE_PATH = os.path.join(os.getcwd(), "sample.docx")
clear(DOCX_FILE_PATH)
clear(DOCX_FILE_PATH, in_place=True)
```
#### Clear metadata for all existing .docx files in the current directory
```python
from dmeta.functions import clear_all
clear_all()
```
#### Update metadata for a .docx file
#### Update metadata for a .docx file in place
```python
import os
from dmeta.functions import update

CONFIG_FILE_PATH = os.path.join(os.getcwd(), "config.json")
DOCX_FILE_PATH = os.path.join(os.getcwd(), "sample.docx")
update(CONFIG_FILE_PATH, DOCX_FILE_PATH)
update(CONFIG_FILE_PATH, DOCX_FILE_PATH, in_place=True)
```

### Update metadata for all existing .docx files in the current directory
#### Update metadata for all existing .docx files in the current directory
```python
import os
from dmeta.functions import update_all
Expand All @@ -96,24 +99,28 @@ update_all(CONFIG_FILE_PATH)

### CLI
⚠️ You can use `dmeta` or `python -m dmeta` to run this program

⚠️ Use `--inplace` to apply the changes directly to the original file.


#### Version
```console
dmeta -v
dmeta --version
```
### Clear metadata for a .docx file
#### Clear metadata for a .docx file in place
```console
dmeta --clear "./test_a.docx"
dmeta --clear "./test_a.docx" --inplace
```
### Clear metadata for all existing .docx files in the current directory
#### Clear metadata for all existing .docx files in the current directory
```console
dmeta --clear-all
```
### Update metadata for a .docx file
#### Update metadata for a .docx file in place
```console
dmeta --update "./test_a.docx" --config "./config.json"
dmeta --update "./test_a.docx" --config "./config.json" --inplace
```
### Update metadata for all existing .docx files in the current directory
#### Update metadata for all existing .docx files in the current directory
```console
dmeta --update-all --config "./config.json"
```
Expand Down
6 changes: 6 additions & 0 deletions dmeta/__main__.py
Original file line number Diff line number Diff line change
Expand Up @@ -37,6 +37,12 @@ def main():
default=False,
help='the `update-all` command updates all metadata in any `.docx` file in the current directory according to the given .json config file.',
)
parser.add_argument(
'--inplace',
action="store_true",
default=False,
help="the `in_place` flag applies the changes directly to the original file."
)
parser.add_argument(
'--config',
nargs=1,
Expand Down
43 changes: 28 additions & 15 deletions dmeta/functions.py
Original file line number Diff line number Diff line change
Expand Up @@ -12,12 +12,14 @@
NOT_IMPLEMENTED_ERROR, FILE_FORMAT_DOES_NOT_EXIST_ERROR


def clear(microsoft_file_name):
def clear(microsoft_file_name, in_place=False):
"""
Clear all the editable metadata in the given microsoft file.
:param microsoft_file_name: name of microsoft file
:type microsoft_file_name: str
:param in_place: the `in_place` flag applies the changes directly to the original file
:type in_place: bool
:return: None
"""
microsoft_format = get_microsoft_format(microsoft_file_name)
Expand All @@ -42,18 +44,23 @@ def clear(microsoft_file_name):
xml_element.text = ""
e_app.write(app_xml_path)

modified = microsoft_file_name[:microsoft_file_name.rfind('.')] + "_cleared"
with zipfile.ZipFile(modified + "." + microsoft_format, "w") as file:

modified = microsoft_file_name
if not in_place:
modified = microsoft_file_name[:microsoft_file_name.rfind('.')] + "_cleared" + "." + microsoft_format
with zipfile.ZipFile(modified, "w") as file:
for file_name in source_file.namelist():
file.write(os.path.join(unzipped_dir, file_name), file_name)
file.close()
shutil.rmtree(unzipped_dir)


def clear_all():
def clear_all(in_place=False):
"""
Clear all the editable metadata in any microsoft file in the current directory.
:param in_place: the `in_place` flag applies the changes directly to the original file
:type in_place: bool
:return: None
"""
path = os.getcwd()
Expand All @@ -64,7 +71,7 @@ def clear_all():
for file in dir_list:
try:
format = get_microsoft_format(file)
clear(file)
clear(file, in_place)
counter[format] += 1
except DMetaBaseError as e:
e = e.__str__()
Expand All @@ -76,14 +83,16 @@ def clear_all():
print("Metadata of {} files with the format of {} has been cleared.".format(counter[format], format))


def update(config_file_name, microsoft_file_name):
def update(config_file_name, microsoft_file_name, in_place=False):
"""
Update all the editable metadata in the given microsoft file according to the given config file.
:param config_file_name: name of .json config file
:type config_file_name: str
:param microsoft_file_name: name of microsoft file
:type microsoft_file_name: str
:param in_place: the `in_place` flag applies the changes directly to the original file
:type in_place: bool
:return: None
"""
config = read_json(config_file_name)
Expand Down Expand Up @@ -123,20 +132,24 @@ def update(config_file_name, microsoft_file_name):
xml_element.text = config[personal_field]
e_app.write(app_xml_path)

modified = microsoft_file_name[:microsoft_file_name.rfind('.')] + "_updated"
with zipfile.ZipFile(modified + "." + microsoft_format, "w") as file:
modified = microsoft_file_name
if not in_place:
modified = microsoft_file_name[:microsoft_file_name.rfind('.')] + "_updated" + "." + microsoft_format
with zipfile.ZipFile(modified, "w") as file:
for file_name in source_file.namelist():
file.write(os.path.join(unzipped_dir, file_name), file_name)
file.close()
shutil.rmtree(unzipped_dir)


def update_all(config_file_name):
def update_all(config_file_name, in_place=False):
"""
Update all the editable metadata in any microsoft file in the current directory according to the given config file.
:param config_file_name: name of .json config file
:type config_file_name: str
:param in_place: the `in_place` flag applies the changes directly to the original file
:type in_place: bool
:return: None
"""
path = os.getcwd()
Expand All @@ -147,7 +160,7 @@ def update_all(config_file_name):
for file in dir_list:
try:
format = get_microsoft_format(file)
update(config_file_name, file)
update(config_file_name, file, in_place)
counter[format] += 1
except DMetaBaseError as e:
e = e.__str__()
Expand Down Expand Up @@ -179,19 +192,19 @@ def run_dmeta(args):
:return: None
"""
if args.clear:
clear(args.clear[0])
clear(args.clear[0], args.inplace)
elif args.clear_all:
clear_all()
clear_all(args.inplace)
elif args.update:
if not args.config:
raise DMetaBaseError(UPDATE_COMMAND_WITH_NO_CONFIG_FILE_ERROR)
else:
update(args.config[0], args.update[0])
update(args.config[0], args.update[0], args.inplace)
elif args.update_all:
if not args.config:
raise DMetaBaseError(UPDATE_COMMAND_WITH_NO_CONFIG_FILE_ERROR)
else:
update_all(args.config[0])
update_all(args.config[0], args.inplace)
else:
tprint("DMeta")
tprint("V:" + DMETA_VERSION)
Expand Down
40 changes: 31 additions & 9 deletions tests/test_dmeta.py
Original file line number Diff line number Diff line change
@@ -1,25 +1,47 @@
from dmeta.functions import update, update_all, clear, clear_all
import os
from dmeta.functions import update, update_all, clear, clear_all

TESTS_DIR_PATH = os.path.join(os.getcwd(), "tests")

def test_clear():
# check the clearance
def test1():
# clear a single .docx file [not inplace]
clear(os.path.join(TESTS_DIR_PATH, "test_a.docx"))


def test_clear_all():
# check all files clearance
def test2():
# clear a single .docx file [inplace]
clear(os.path.join(TESTS_DIR_PATH, "test_a.docx"), in_place=True)


def test3():
# clear all existing .docx files [not inplace]
os.chdir(TESTS_DIR_PATH)
clear_all()


def test_update():
# test meta-data is updated
def test4():
# clear all existing .docx files [inplace]
os.chdir(TESTS_DIR_PATH)
clear_all(in_place=True)


def test5():
# update a single .docx file [not inplace]
update(os.path.join(TESTS_DIR_PATH, "config.json"), os.path.join(TESTS_DIR_PATH, "test_a.docx"))


def test_update_all():
# test all files meta-data are updated
def test6():
# update a single .docx file [inplace]
update(os.path.join(TESTS_DIR_PATH, "config.json"), os.path.join(TESTS_DIR_PATH, "test_a.docx"), in_place=True)


def test7():
# update all existing .docx files [not inplace]
os.chdir(TESTS_DIR_PATH)
update_all(os.path.join(TESTS_DIR_PATH, "config.json"))


def test8():
# update all existing .docx files [inplace]
os.chdir(TESTS_DIR_PATH)
update_all(os.path.join(TESTS_DIR_PATH, "config.json"), in_place=True)

0 comments on commit 787d254

Please sign in to comment.