MetaData収集ひな形(PysimpleGUI,HTML)


はじめに

データを収集するとき、そのデータの説明であるメタデータも同時に収集することが重要です。データを提供してくれる人に「データの説明をつけてください」とお願いしてもなかなか難しいので、こちらであらかじめデータ説明のテンプレートをつける必要があります。もっとも簡単なのはEXCELですが、フォーマットが勝手に変えられていたりと意外に、そのあとの処理が面倒なことがあります。

そこで、(1)HTMLのFileAPIとJavascriptを用いて、オフラインで必要な情報を入れることができるHTMLファイルを配り、情報を入れてJSONファイルにして出力するひな形と(2)PysimpleGUIで作成したひな形、を覚えとして記載します。

環境(Python)

Win10Pro
Anaconda
Python3.7

Visual studio code

インストールモジュール
PySimpleGUI

HTML + Javascript

HTMLのFileAPIとJavascriptを用いて、オフラインで必要な情報を入れるHTMLファイルを配り、情報を入れてJSONファイルにして提供してもらうタイプ。
参考:
(1) JavaScriptのオブジェクト(連想配列)をjsonファイルとしてダウンロードする
(2) JavaScriptでファイル操作!? File APIを使いこなそう (1/2)
(3) Blob と File クラスについて

参考(1)をほぼコピーペーストしただけです。

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <title>Title</title>
    <link rel="stylesheet" type="text/css" href="main.css">
</head>

<body>
    <div id="json_root">
        <ul id="base">
            <li>
                <label for="name"> Name:</label>
                <input type="text" id="name" placeholder="input name" />
            </li>
            <li>
                <label for="description"> description:</label>
                <input type="text" id="description" placeholder="description" />
            </li>
            <li>
                <label for="filename"> File Name:</label>
                <input type="text" id="filename" placeholder="file name" />
            </li>
            <li>
                <label for="comment"> comment:</label>
                <input type="text" id="comment" placeholder="comment" />
            </li>
        </ul>
    </div>

    <button id="download">ダウンロード</button>

    <script type="text/javascript">
        window.onload = () => {
            const download = document.getElementById('download');
            const getData = () => {
                return {
                    name: document.getElementById('name').value,
                    description: document.getElementById('description').value,
                    filename: document.getElementById('filename').value,
                    comment: document.getElementById('comment').value,
                };
            };

            download.addEventListener('click', function() {
                const data = getData();
                const blob = new Blob([JSON.stringify(data, null, '  ')], {
                    type: 'application\/json'
                });
                const url = URL.createObjectURL(blob);
                const link = document.createElement('a');
                link.href = url;
                link.download = document.getElementById('name').value + '.json';
                link.click();
                URL.revokeObjectURL(url);
            });
        };
    </script>
</body>

</html>

実行すると以下のようになります。

Python

あまりHTML、Javascriptが得意ではないので、それと同じ機能をPysimpleGUIで作成しました。配布するにはexe形式にするのが良いのですが、なかなか面倒なので今回はそのままです。

"""
Metadata -> JSON

"""
import re
from pathlib import Path
import json

import PySimpleGUI as sg

sg.theme('Light Blue 2')

# MetaDataにしたいKeyのリストを作成
key_lists = ['name','description','filename', 'comment']

layout_list = []
for key_name in key_lists:
    temp =[]
    temp = [sg.Text(f'{key_name}', size=(12, 2)),sg.InputText(size=(60, 2),key=f'-{key_name}-')]
    layout_list.append(temp)
layout_list.append([sg.Text('Save path', size=(12, 2)),sg.InputText(default_text='./data',key='-savepath-')])
layout_list.append([sg.Submit(), sg.Cancel()])

window = sg.Window('Metadata to JSON', layout_list)

while True:
    event, values = window.read()
    if event in (None, 'Cancel'):
        break
    elif event in 'Submit':

        data_dict ={}
        for i in key_lists:

            #この辺りは好きにアレンジ
            # タブや改行は削除
            data_value =re.sub('\t|\n', '', values[f'-{i}-'])
            # data_value = ' '.join(data_value.splitlines())

            # 先頭の空白だけ削除
            data_dict[f'{i}'] = data_value.lstrip() 

        # print(f'Data: {data_dict}')

        # Save Path & save name
        Path(values['-savepath-']).mkdir(exist_ok=True)
        file_name = '{}/{}.json'.format(values['-savepath-'],data_dict[key_lists[0]])

        # 辞書型をJSONに変換してSave
        with open(file_name, 'w') as f:
            json.dump(data_dict, f, indent=4)

        # 入力されているデータをクリア
        for key_name in key_lists:
            window[f'-{key_name}-'].update('')

window.close()

実行するとGUIが立ち上がります。

メタデータを入力してSubmitを押すとJSONファイルが作成されて、入力したデータがクリアーされます。

メタデータはJSON形式で保存されます。

JSON形式で保存されているので、後の処理は簡単にできるのではないでしょうか?YAMLファイル形式でもよいかもしれません。

まとめ

データ分析を行う上でメタデータは重要ですが、それを集めて整理するのはなかなか面倒です。PysimpleGUIをコンパイルして配ることを考えるとhtmlファイルの配布の方がやっぱり楽かな。