【業務効率化】pythonのコードを社内のみんなに使ってもらう方法

# 目次
* 背景
* 目的
* 結論
* 内容
* まとめ
* 所感

# 背景
pythonを頑張って勉強して[業務効率化できるコード](https://qiita.com/r-shiomoto/items/a54fca6463fa128ac5ef)を作成しました。これを社内の人に使ってもらおうと思っても、みんなのPCには当然pythonはインストールされていません。その結果、せっかく作成したコードは社内では利用できず、自己満足で終わってしまうことがありました。

# 目的
作成したコードを社内のみんなに使ってもらう方法を調査すること。

# 結論
1位：USBメモリにpython環境を作成する
2位：exe化して配布する
3位：Webアプリを作成する

# 内容
作成したコードを社内のみんなに使ってもらう方法を、完全主観の個人的ランキング形式で紹介します。

## 1位：USBメモリにpython環境を作成する
USBメモリ内にpythonをダウンロードして、その中でコードを実行してもらう方法です。使い方としては、USBメモリをPCに挿入して、その中のバッチファイルをクリックすることでpythonコードを実行します。
メリットは、構築が簡単なこと、機能拡張やメンテンスが容易なことです。デメリットは、同時複数人の使用ができないこと、セキュリティが厳しい環境ではそもそもUSBメモリの使用が禁止されていることです。

作成方法は[このサイト](https://gammasoft.jp/blog/python-and-jupyterlab-in-usb-stick/)を参考にして説明します。参考サイトはjupyterlabを使用できるようにしていますが、これを応用して単発のコードを実行できるようにします。

### 1. 作業用フォルダを作成する。
PC内のどこでもいいので、作業用フォルダ`PythonUSB`を作成してください。その配下に`python`フォルダと`code`フォルダを作成します。この`PythonUSB`は最終的にUSBメモリにそのままコピーします。
```
├directory
│    └ PythonUSB/     <= 作業用フォルダー
│         ├ python/
│         └ code/
```

### 2. pythonをダウンロードして配置する 
[pythonのページ](https://www.python.org/downloads/)から、OSに合わせたダウンロードページに遷移してください。今回はWindowsで説明します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/8a6a9944-f5eb-a499-d3c9-4f6ffe12387d.png)

Windowsのリンク先に行くと、バージョンがいくつかありますが、OSのbitに合わせたembeddableパッケージをダウンロードします。今回は、執筆時点で最新の3.12.0バージョン、64-bitを上述の`python`フォルダにダウンロードします。ダウンロードが完了したら、解凍しましょう。解凍後のフォルダ名が`python-3.12.0-embed-amd64`と長いので、`python-3.12.0`に変更します。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/45f8f570-ad76-2ab5-e82a-e83c8ef83fbb.png)

### 3. pipを使えるようにする
先程の`python-3.12.0`フォルダ内に`python312._pth`がありますので、これをメモ帳で開きます。そして、`#import site`の`#`を削除して`imoprt site`に変更して保存します。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/f83cd533-f145-5952-fe58-b0907f7ca072.png)

続いて、[get-pip.py](https://bootstrap.pypa.io/get-pip.py)のリンクを右クリックして「名前をつけてリンク先を保存」で`python-3.12.0`フォルダにダウンロードします。
このファイルをコマンドプロンプトで実行するには、`python-3.12.0`フォルダをエクスプローラーで開き、アドレスに「cmd」と入力してEnterを押して、コマンドプロンプトを出現させます。そして、`python.exe get-pip.py`を実行します。
これで`pip install`が使用することができるようになりました。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/a9dae7e5-65eb-6d96-03e6-d89285bf1f99.png)

### 4. 使用するライブラリをインストールする
インストールするには、コマンドプロンプトで`python-3.12.0`フォルダに移動して、`python.exe -m pip install [ライブラリ]`を実行します。例えば、エクセルを操作するライブラリ`openpyxl`をインストールするには以下のようにします。必要なライブラリを順次インストールしてください。

```
python.exe -m pip install openpyxl
```

### 5. 実行用バッチファイルを作成する
バッチファイルをクリックするだけでコードが実行できるようにします。`execute.bat`を以下の位置に作成します。メモ帳のテキストファイルからファイル名を変更することで作成できます。今回は`hello.py`というpythonファイルを実行する例を紹介します。
```
├directory
│    └ PythonUSB/     <= 作業用フォルダー
│         ├ python/
│         └ code/
│             └ hello.py
│         └ execute.bat
```

`hello.py`の中身は以下の通りです。最後に`input`関数を入れておくことで、コマンドプロンプトが自動で閉じるのを防いでいます。
```python hello.py
print('Hello world!')

input('Close window to enter any key.')
```

`execute.bat`の中身は以下の通りです。
`@echo off`がないと、`set`以下の内容がコマンドプロンプト上に表示されてしまいます。見栄えの問題ですね。
`set xxx=yyy`は変数を定義しています。この変数を利用する際には、`%`で挟んで上げる必要があります。
`%~dp0`は実行されるバッチファイルが置かれているカレントディレクトリを示します。今回の場合では、PythonUSBですね。
`pyintpath`は`python.exe`までのパス、`codepath`は`code`までのパス、`pyfile`は実行したいpyファイル名の変数を設定します。
`%pyintpath%python.exe %codepath%%pyfile%`は、上述の変数を組み合わせてよく使う`python xxx.py`の形式になっています。

```execute.bat
@echo off
set cwdirpath=%~dp0
set pyintpath=%cwdirpath%python\python-3.12.0\
set codepath=%cwdirpath%code\
set pyfile=hello.py

%pyintpath%python.exe %codepath%%pyfile%
```

実行結果は以下の通りです。意図通りの動きをしています。
![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/30092e12-ee8d-3bf5-21a1-4289c72b88fd.png)

### 6. USBメモリにコピーする
「PythonUSB」フォルダをUSBメモリにコピーします。コピー先でもバッチファイルが実行できるか念のため確認しておきましょう。今回のような単純なコードなら40MBほどの容量で十分ですが、jupyterlabを使用したい場合は1GB以上のUSBメモリを用意しましょう。
「PythonUSB」フォルダをそれぞれのPCにコピーしても、もちろんコードを実行することはできますが、機能追加や保守管理の観点からあまりオススメはできません。修正がある度にUSBメモリからコピーしなくてはならなくなります。

一つ注意が必要なのは、開発したOS環境と使用するOS環境が一致させることです。例えば、windows11で「PythonUSB」フォルダを作成してUSBメモリにコピーし、window10で使用してもコードは実行できません。

## 2位：exe化して配布する
exeファイルを作成して、そのファイルをみんなのPCに配布して実行する方法です。
メリットとしては、配布が容易であることです。デメリットは、保守管理が難しいこと、セキュリティが厳しい環境ではウイルス対策ソフトにブロックされることもあること (開発元不明のexeファイルが実行できないなど)です。また、完全にパッケージ化してしまうので、後からバグが見つかっても、一部を修正するということはできず、再度exe化する必要があります。

exe化するライブラリはいくつかありますが、ここではPyInstallerの例で紹介していきます。

### 1. 仮想環境を作成する
exe化する際にビルド環境にある全てのライブラリを含んでしまうため、無駄なライブラリを含まないように仮想環境を作成し、必要なライブラリのみインストールされた環境でexe化します。
今回はvenvを使用して、`test_env`という名前の仮想環境を作成します。
```
cd 仮想環境を作りたいフォルダのパス
python -m venv test_env
```

### 2. ライブラリをインストールする
仮想環境をアクティブにしてから、コードの実行に必要なライブラリをインストールしていきます。exe化に必須な`pyinstaller`のインストールを忘れずに。

```shell
pip install 必要なライブラリ
pip install pyinstaller
```

### 3. exe化する
exe化するには、`pyinstaller exe化したいpyファイル`というコマンドを打ちます。今回は、「1位：USBメモリにpython環境を作成する」で使用した`hello.py`をexe化します。

```
pyinstaller hello.py
```

すると、以下のようなディレクトリとファイルが生成されます。この内、dist/code/hello/hello.exeが実行ファイルになります。

```
├directory
│    ├ build/
│    ├ dist/
│    │   └ code/
│    │      └ hello/
│    │          ├ ...
│    │          ├ ...
│    │          └ hello.exe   <=実行ファイル
│    ├ hello.py
│    └ hello.spec
```

しかし、これだと実行ファイルを見つけるのが大変です。pyinstallerには、実行ファイルを1つにまとめるオプションがあります。先程のexe化コマンドに`--onefile`を追加するだけです。

```
pyinstaller hello.py --onefile
```

すると、以下のようなディレクトリとファイルが生成されます。この内、dist/hello.exeが実行ファイルになります。

```
├directory
│    ├ build/
│    ├ dist/
│    │  └ hello.exe   <=実行ファイル
│    ├ hello.py
│    └ hello.spec
```

### 4. exeファイルを配布する
このexeファイルをメールで送付する前に動作確認をしましょう。exe化したファイルが動作しないという事象が度々あります。
また、exeファイルの容量に注意しましょう。今回の単純なファイルだけでも5.8MBの容量を有しています。[また、condaでインストールしたpandasをexe化するとかなりファイル容量が大きくなることが知られています](https://work-life-enj.com/use-pyinstaller/)。動作と容量を確認してから配布を行いましょう。


## 3位：Webアプリを作成する
社内にサーバを立てて、そこにWebアプリのコードを格納して実行する方法です。使い方としては、指定したURLにみんながアクセスする形になります。
メリットとしては、同時複数人の使用ができること機能拡張やメンテンスが容易なことです。デメリットとしては、学習コストが高いこと、サーバを立てるのに費用がかかること、ネットワークセキュリティを考える必要があることです。

ここでは具体的なコードは紹介しませんが、ロードマップを示します。[私の過去の投稿「【体験記】非プログラマーがRaspberry piにウェブアプリを実装し、化学系企業の社内に導入した件」](https://qiita.com/r-shiomoto/items/30a5267ca47ef5d9b919)を参考にしてもらえると何かヒントを得られるかもしれません。

### 1. DjangoもしくはFlaskを勉強する
DjangoとFlaskはどちらもWebアプリを作成するためのpythonのライブラリです。DjangoはFlaskに比べて学習コストが高い分、より多くの機能を実装することができます。Webアプリを作成するためのライブラリといっても、HTMLやCSSを全く学習しなくて良いというわけではありません。イメージとしては、pythonで処理した情報をHTMLに埋め込んだり、HTMLから発信された情報をpythonで処理したりする感じです。見栄えを整えるにはCSSの知識も必要です。
pythonしか扱えない方がこの方法を採用する際には、それ相応の学習コストがかかることを覚悟しておいてください。

### 2. サーバを立てる
私はサーバの知識を殆ど持ち合わせていないのですが、Windows Serverのような本番環境で使用するようなサーバは高価で、業務効率化のコードを実行するためだけに購入するのは費用対効果が見合っていません。既存の社内サーバに上乗せするのも何かとリスクがあるように感じられます。また、社内の情報を取り扱うコードの場合、クラウドのレンタルサーバの使用はためらわれます。
そこでオススメなのが、[Raspberry pi (ラズパイ)](https://ja.wikipedia.org/wiki/Raspberry_Pi)です。ラズパイとはシングルボードコンピュータであり、IoTや電子工作にも使えますが、サーバとしても機能します。価格もケースや給電コードを含めて4万円ほどでAmazonで購入できます。ラズパイの中にDjango及び実行コードを実装することで、社内ネットワーク内なら誰でもアクセスできるようになります。

![image.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/2672794/5cbb6798-32dc-08a3-73c5-0cc6741d7abe.png)

しかしながら、サーバとして利用するためには色々と設定する事項があります。IPアドレスの固定、Apacheの設定など、このステップでもある程度の知識が求められますが、ネットで調べればなんとかできる範囲です。

### 3. ネットワークセキュリティ
ラズパイはNASAでも使用されるコンピュータですが、[NASAはラズパイ経由でサイバー攻撃を受けた過去があります](https://www.itmedia.co.jp/news/articles/1906/23/news012.html)。したがって、ネットワークセキュリティは適切に行わなければなりません。
まずは初期のユーザー名とパスワードを変更することです。一昔前は、ラズパイOSをインストールしたら、ユーザー名pi、パスワードraspberryがデフォルト設定されており、この情報を知っていれば、外部からRaspberry piに不正アクセスされるリスクがありました。現在ではOS導入するインストーラ (Imager)の段階でユーザー名とパスワードを設定できます。他にも考えるべき事項 (そもそもネットワークに接続しても良いのか、ウイルス対策ソフトをインストールする必要はあるかなど)はあるかと思いますが、そこは社内の情報システム部と相談の上、対応するのがベストかと思います。

### 4. 社内で許可を得る
上記でも少し触れましたが、ここが一番大切な部分だと思います。Webアプリはネットワークを通じていますので、内容を説明すべきステークホルダーが多くなるのは必然です。どのようなレポートラインを辿るか、部署に合わせた説明資料が必要となってきます。まずは、直属の上司に相談することから始めてみましょう。業務効率化に寄与するのですから、嫌な顔をする上司はいないでしょう。受けが悪かった場合に備えて、開発予定の機能も伝えるとよいかもしれません。


# まとめ

3つの方法を紹介しましたが、それぞれについて評価軸を設けて比較してみます。

<table>
<thread> <th> 
               <td>USBメモリにpython環境を作成する</td> <td>exe化して配布する</td> <td>Webアプリを作成する</td>
</th> </thread>

<tr> <td>構築の難易度</td> <td>◎</td> <td>◯</td> <td>☓</td> </tr>
<tr> <td>コードの保守管理性</td> <td>◯</td> <td>☓</td> <td>◎</td> </tr>
<tr> <td>同時複数人の利用</td> <td>☓</td> <td>◯</td> <td>◎</td> </tr>
<tr> <td>費用</td> <td>◯</td> <td>◎</td> <td>☓</td> </tr>
<tr> <td>セキュリティ</td> <td>△</td> <td>△</td> <td>△</td> </tr>
</table>

ベストな方法はなく、共有したいコードの性質や社内のセキュリティ事情によって、より良い方法を選択することが大切です。例えば、利用頻度が低く、複雑なコードで改修する可能性があるコードなら、USBメモリの方法が良いと考えられ、毎日何度も利用する簡単なコードならexe化方法が良いです。Webアプリの方法は、学習コストが高いことから中々手を出しにくい方法ですが、プログラミングの勉強をするモチベーションを与えてくれると思います。

# 所感

これまで試してきた方法を紹介しましたが、やはり人のために環境を整えるのは骨が折れます。それでも、「これは便利！」と言ってもらえると、苦労した甲斐があったなと思えますし、ほんの少しの業務効率化が多くの人に長期的に適用されることで、トータルで見ると膨大な量の業務削減になり、より生産性の仕事をすることに集中できると思います。
もっと良い方法があるという方やこんな方法でコードを共有したなどのエピソードがあれば、コメントしてくれると嬉しいです。

この記事が誰かの役に立つことを願っております。
最後まで読んでいただき、ありがとうございました。:v: