LoginSignup
0
0

More than 1 year has passed since last update.

この煩わしい添付ファイルの送受信を

Last updated at Posted at 2023-04-26

はっきり言って面倒なやり方です。
手間を惜しまず、パスワード付き zip ファイル等を
送受信したい方達向けです。

大雑把に言うと
メール本文に復元アプリと添付ファイル(データ)を貼付、送信
受信側は、受け取った復元アプリを実行して添付ファイルを復元

Eメールに特定のファイルを添付すると
ウィルス対策により、メーラーに弾かれてしまったりとか
送信出来ても受信側が受け付けない場合が有ります。

外部の送信システムを使わないで送信したい場合は
添付ファイルを「文」としてメール本文に展開して
送信を行えば手間は掛かりますが可能になります。

ただし、ファイル容量は約60MBくらいが限界です。
※ バッチで使用する Certutil コマンドの作成限界

環境は、送受信ともに Windows で
PowerShell が 実行可能であることです。

受信側は、Windows でなくても
Base64 を 復号出来る環境なら何でも大丈夫です。

送信側の作業

 送信準備-① 作業フォルダを作成してメール本文生成アプリを保存
 送信準備-② 送信する添付ファイルを1つの書庫に纏めて作業フォルダへ保存
 送信準備-③ メール本文を生成して、クリップボードに送るアプリを実行
 送信処理-④ クリップボードの中身をメール本文に貼付後、送信

       * * * 送信するメール本文 * * *

       復元アプリ①のファイル名
       復元アプリ①の内容

       復元アプリ②のファイル名
       復元アプリ②の内容

       【変換された添付ファイル】

受信側の作業

 復元準備-① 作業フォルダを作成してメール本文の復元アプリを保存
 復元処理-② メール本文の添付ファイルを復元

 作業フォルダに添付ファイルが作成されます。


復元するコードは、こちらを利用しています。

Base64エンコードされたデータを 実体ファイルに一括復元する「マジック生成」バッチ (PowerShellによる高速処理版)
https://qiita.com/Yunixuma/items/1db1929775e34ac7ef01


送信側の作業

送信準備-① 作業フォルダを作成してメール本文生成アプリを保存

      ● 作業用のフォルダを作り
        「②ファイルの選択を行うダイアログ.ps1」と
        「③MSGBOX.VBS」と
        「①メール本文を作成してクリップボードへ送る【★ダブルクリックするのはコレ★】.cmd」
        を同じフォルダにファイルを作成して
        文字コード を ANSI で保存する

送信準備-② 送信する添付ファイルを1つの書庫に纏めて作業フォルダへ保存

      ● 【 7zip ※ 拡張子 7z 】・【 zip 】・【 cab 】の
        どれかを選択して書庫ファイルを作成し
        送信準備-①で作成した作業用フォルダに保存する

      ※ 送信対象のファイルが一つで 7zip,zip,cab 形式のどれかなら
        そのまま送信準備-①で作成した作業用フォルダに保存する

      ※ エンコード(符号化)でサイズが増加し
        Certutil コマンドの作成限界が約60MBなので
        受信側が受取可能ならば書庫は 7zip での高圧縮が望ましい

送信準備-③ メール本文を生成して、クリップボードに送るアプリを実行

      ● 「①メール本文を作成してクリップボードへ送る【★ダブルクリックするのはコレ★】.cmd」
        を ダブルクリックで実行
        ファイル選択ダイアログが表示されるので
        送信準備-② で用意したファイルを選択する

        例 添付.zip を 選択すると 添付.zip.TXT と メール本文.txt が
         送信準備-①で作成した作業用フォルダに作成される

        ファイルの選択後、クリップボードに送る内容を選択
        アプリとデータを送る場合は、【 はい 】をクリック
        データのみを送る場合は、【 いいえ 】をクリック
        クリップボードに送らない場合は、【 キャンセル 】をクリック

        送信先の復元環境が用意されていない場合は
        アプリとデータを送って下さい。

送信処理-④ クリップボードの中身をメール本文に貼付後、送信
送信.png
      ※ Gmail の場合、サイズが大きいと処理落ちするので
        メール本文.txt をメモ帳で開き
        先頭のアプリの部分を一度貼付けてから
        残りを貼付けると成功しました。


受信側の作業

復元準備-① 作業フォルダを作成してメール本文の復元アプリを保存

      ● 作業用のフォルダを作り
        「①復元するアプリ【★ダブルクリックするのはコレ★】.bat」 と
        「②復元するアプリ.ps1」
        を同じフォルダにファイルを作成して
        文字コード を ANSI で保存する

復元処理-② メール本文の添付ファイルを復元

      ● メール本文の「↓↓↓↓↓↓↓↓」の
        次の行から -----END CERTIFICATE-----
        までをクリップボードにコピーする

        下記の例の場合

        「クリップボードに送る内容」

        ↓↓↓↓↓↓↓↓
        添付.zip
        -----BEGIN CERTIFICATE-----
        r2J3btgBxX2vYndu2AFQSwUGAAAAAAEAAQByAAAAXAAAAAAA
        -----END CERTIFICATE-----

        の 添付.zip から 4行を選択して、
        右クリックメニューでコピーする
メール本文コピー.png
      ● 「①復元するアプリ【★ダブルクリックするのはコレ★】.bat」 を ダブルクリックで実行
        上記の例の場合、作業用のフォルダに 添付.zip が作成される

②ファイルの選択を行うダイアログ.ps1
Set-StrictMode -version Latest

#.NET Frameworkのダイアログ関連オブジェクトの取り込み
Add-Type -assemblyName System.Windows.Forms

#ファイル選択ダイアログのオブジェクト取得
$dialog   = New-Object System.Windows.Forms.OpenFileDialog

#タイトルの設定
$dialog.Title = "エンコードするファイルを選択して下さい"

#フィルタ条件の設定
$dialog.Filter = '圧縮ファイル|*.7z;*.cab;*.zip'

#デフォルト選択ディレクトリの設定
$dialog.InitialDirectory = '.'

if ($dialog.ShowDialog() -eq "OK") {
    '"' + $dialog.FileName + '"'
  } else {
    '未選択'
}

③MSGBOX.VBS
Option Explicit
REM ------------------------------------------------------
REM msgbox.vbs str1 , str2 [,mode]
REM     str1:表示するメッセージ
REM     num :表示するボタンの選択
REM     str2:メッセージボックスのタイトル
REM (動作)
REM メッセージボックスを表示し、クリックされたボタンを
REM 返します。
REM str1 中の 「crlf」という文字列は改行に変換します。
REM ・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・
REM ボタンの表示選択と動作などの設定(ボタン表示や動作などの値を合計します。)
REM     0 [OK] ボタンのみを表示します。
REM     1 [OK] ボタンと [キャンセル] ボタンを表示します。
REM     2 [中止]、[再試行]、および [無視] の 3 つのボタンを表示します。
REM     3 [はい]、[いいえ]、および [キャンセル] の 3 つのボタンを表示します。
REM     4 [はい] ボタンと [いいえ] ボタンを表示します。
REM     5 [再試行] ボタンと [キャンセル] ボタンを表示します。
REM    16 警告メッセージ アイコンを表示します。
REM    32 問い合わせメッセージ アイコンを表示します。
REM    48 注意メッセージ アイコンを表示します。
REM    64 情報メッセージ アイコンを表示します。
REM     0 第 1 ボタンを標準ボタンにします。
REM   256 第 2 ボタンを標準ボタンにします。
REM   512 第 3 ボタンを標準ボタンにします。
REM   768 第 4 ボタンを標準ボタンにします。
REM     0 アプリケーション モーダルに設定します。
REM       メッセージ ボックスに応答するまで、現在選択中のアプリケーションの実行を継続できません。
REM  4096 システム モーダルに設定します。
REM       メッセージ ボックスに応答するまで、すべてのアプリケーションが中断されます。
REM ・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・・
REM 戻り値となる文字列
REM   ボタンの名前     -> respondの戻り値
REM     [OK]           -> Ok
REM     [キャンセル]   -> Cancel
REM     [中止]         -> Stop
REM     [再試行]       -> Retry
REM     [無視]         -> Ignore
REM     [はい]         -> Yes
REM     [いいえ]       -> No
REM ------------------------------------------------------
Dim args, arg(99), v, cnt
Dim str1, str2
Dim mode
Dim respond, eLevel
Dim CRLF
REM 改行符号を設定します。
CRLF = chr(13) & chr(10)
Set args = WScript.Arguments
cnt = 1
For Each v In args
    arg(cnt) = v
    cnt = cnt + 1
Next
REM 改行文字の置き換え
arg(1) = RepExAll (arg(1), "crlf", CRLF)
eLevel = 0
Select Case args.Count
    Case 0:    mode = 0: eLevel = 1
    Case 1:    mode = MsgBox (arg(1))
    Case 2:    mode = MsgBox (arg(1), arg(2))
    Case Else: mode = MsgBox (arg(1), arg(2), arg(3))
End Select
Select Case mode
    Case 0: respond = ""
    Case 1: respond = "Ok"
    Case 2: respond = "Cancel"
    Case 3: respond = "Stop"
    Case 4: respond = "Retry"
    Case 5: respond = "Ignore"
    Case 6: respond = "Yes"
    Case 7: respond = "No"
End Select
REM 結果の表示
WScript.Echo respond
WScript.Quit (eLevel)
REM ここからサブルーチン=========================================
REM 原稿文字列を正規文字列で検索し、一致する文字をすべて置換文字列に置き換えます。
REM s : 原文字列
REM t : 正規文字列
REM d : 置換文字列
Function RepExAll ( s , t , d )
    Dim regExpression, Matches                ' 変数を作成します。
    Set regExpression = New RegExp            ' 正規表現を作成します。
    regExpression.Pattern    = t              ' パターンを設定します。
    regExpression.IgnoreCase = True           ' 大文字と小文字を区別しないように設定します。
    regExpression.Global     = True           ' 文字列全体を検索するように設定します。
    RepExAll = regExpression.Replace(s , d)   ' 置換を実行します。
End Function

①メール本文を作成してクリップボードへ送る【★ダブルクリックするのはコレ★】.cmd
@echo off

rem /;
rem /; ★ メール本文を生成してクリップボードへ送る
rem /;    ◆ エンコード(符号化)する圧縮書庫をダイアログで選択 ※ cab形式 zip形式 7z形式
rem /;    ◆ エンコードのファイル名を生成
rem /;    ◆ 圧縮書庫をエンコード
rem /;    ◆ メール本文を生成
rem /;    ◆ 生成されたメール本文をクリップボードへ送る
rem /;

rem /;
rem /; ◆ エンコード(符号化)する圧縮書庫をダイアログで選択 ※ cab形式 zip形式 7z形式
rem /;

for /f "delims="                   %%0 in ('Powershell -NoProfile -ExecutionPolicy unrestricted -f "%~dp0②ファイルの選択を行うダイアログ.ps1"') do (
    if  not                       "%%0"=="未選択" (
        set               ARC_File=%%0
      ) else (
        msg               console "ファイルが未選択です。OK を クリックで終了します。"
        goto              :eof
    )
)

rem /;
rem /; ◆ エンコードのファイル名を生成
rem /;
rem /;    選択されたファイルの拡張子の後ろに .TXT を付加したファイル名を作成
rem /;
rem /;    ARC_File     "c:\test\添付.zip"
rem /;                       ↓
rem /;    ARC_File_TXT  c:\test\添付.zip.TXT
rem /;

for /f "delims=" %%0 in (%ARC_File%) do set                                    "ARC_File_TXT=%%~dpnx0.TXT"

rem /;
rem /; ◆ 圧縮書庫をエンコード
rem /;
rem /;    エンコード(符号化)前に作成するファイルを削除してから
rem /;    選択されたファイルを Base64 で エンコード(符号化)
rem /;
rem /;                 "c:\test\添付.zip" ⇒  "c:\test\添付.zip.TXT"
rem /;
rem /;    添付.zip                                   > 添付.zip.TXT
rem /;    -----BEGIN CERTIFICATE-----                > メール本文.txt
rem /;
rem /;    添付.zip.TXT
rem /;    添付.zip
rem /;    -----BEGIN CERTIFICATE-----
rem /;

for /f "delims=" %%0 in (%ARC_File%) do echo;%%~nx0>                          "%ARC_File_TXT%"
del /f /q                                            "%~dp0メール本文.txt" > nul 2> nul
certutil -encode         %ARC_File%                  "%~dp0メール本文.txt"
type                                                 "%~dp0メール本文.txt" >> "%ARC_File_TXT%"

rem /;
rem /; ◆ メール本文を生成
rem /;

(
echo;①復元するアプリ【ダブルクリックするのはコレ】.bat
echo;@ECHO OFF
echo;PowerShell -ExecutionPolicy RemoteSigned -STA -File "%%~dp0②復元するアプリ.ps1" %1 "nul"
echo;DEL  /f                                             "%%~dp0②復元するアプリ.log"
echo;EXIT /B
echo;
echo;--------------------------------------------------------------------------
echo;
echo;②復元するアプリ.ps1
echo;$Host.UI.RawUI.ForeGroundColor = "Green"
echo;Add-Type -Assembly System.Windows.Forms
echo;"############# B642FHT.ps1 ##############"
echo;"# Converting data sequence             #"
echo;"#            encoded in Base64         #"
echo;"#       to real files continuously     #"
echo;"# high-throughput script by PowerShell #"
echo;"#                                      #"
echo;"#   1st release: 2019-07-07            #"
echo;"#   Last update: 2019-07-25            #"
echo;"#   Author: Y. Kosaka                  #"
echo;"#   See the web for more information   #"
echo;"#   https://qiita.com/x-ia             #"
echo;"########################################"
echo;
echo;$filenameScript = ^(Get-ChildItem $MyInvocation.MyCommand.Path^).BaseName
echo;$dirPathScript = Split-Path $MyInvocation.MyCommand.Path -Parent
echo;$Host.UI.RawUI.WindowTitle = $filenameScript
echo;$extLog = ".log"
echo;$timePause = 1500
echo;
echo;
echo;function ChDirWork^($arg^) {
echo;  if ^(Test-Path $arg.Replace^('"', '')) {
echo;    ChDir $arg
echo;    [System.IO.Directory]::SetCurrentDirectory^(^(Get-Location -PSProvider FileSystem^).Path^)
echo;  }
echo;}
echo;
echo;function GetClip {
echo;  $strClip = [Windows.Forms.Clipboard]::GetText^(^)
echo;  return $strClip
echo;}
echo;
echo;function ViewClip^($strClip^) {
echo;  $numSizeClip = $strClip.Length
echo;  $numLineClip = 0
echo;  foreach^( $strLine in $strClip -split "`r`n" ^){
echo;    ++$numLineClip
echo;  }
echo;  Write-Host "`r`nRead $($numSizeClip.ToString("#,#")) chars ($($numLineClip.ToString("#,#")) lines) from the clipboard.`r`n"
echo;  return $numLineClip
echo;}
echo;
echo;function DivText^($strClip, $numLineClip, $filenameScript, $extLog^) {
echo;  $strOut = $null
echo;  $flagOut = 0
echo;  $numOut = 0
echo;  $numProgressNext = 0
echo;  $numLineProcessed = 0
echo;  foreach^( $strLine in $strClip -split "`r`n" ^){
echo;    if ^(^($strLine -like "``````*"^) -Or ^($strLine -like "---*"^)^) {
echo;      $flagOut +=1
echo;      if ^($flagOut -eq 1^) {
echo;        $fileOut = $strLinePrev
echo;      } elseif ^($flagOut -eq 2^) {
echo;        $err = DecodeB64 $strOut $fileOut
echo;        PutLog $err $fileOut $filenameScript $extLog
echo;        $numOut += 1
echo;        $strOut = $null
echo;        $flagOut = 0
echo;      }
echo;    } elseif ^($flagOut -eq 1^) {
echo;      $strOut += $strLine
echo;    } else {
echo;    $strLinePrev = $strLine
echo;    }
echo;    $numLineProcessed += 1
echo;    $numProgress = [Math]::Floor^(100 * $numLineProcessed / $numLineClip^);
echo;    if ^($numProgress -ge $numProgressNext^) {
echo;      Write-Progress -activity "Processing the text from clipboard" `
echo;      -status "$numProgress %% processed" `
echo;      -percentComplete $numProgress `
echo;      -CurrentOperation "$($numLineProcessed.ToString("#,#")) / $($numLineClip.ToString("#,#")) lines, $numOut files created."
echo;      $numProgressNext = $numProgress + 1
echo;    }
echo;  }
echo;}
echo;
echo;function DecodeB64^($strOut, $fileOut^) {
echo;  [System.IO.File]::WriteAllBytes^($fileOut, [Convert]::FromBase64String^($strOut^)^)
echo;  return $?
echo;}
echo;
echo;function PutLog^($err, $fileOut, $filenameScript, $extLog^) {
echo;  if ^("$err" -eq "True"^) {
echo;    $strResult = "Success"
echo;    Write-Host "Suceeded to create a file $fileOut."
echo;  } else {
echo;    $strResult = "Failure"
echo;    Write-Host "Failed. An error occured."
echo;  }
echo;  $timeStampNow = ^(Get-Date^).ToString^("yyyy-MM-dd HH:mm:ss.fff"^)
echo;  $fileLog = $filenameScript + $extLog
echo;  "$timeStampNow`t$filenameScript`t$strResult`t$fileOut" ^| `
echo;  Out-File $fileLog -Encoding Default -Append
echo;  $Host.UI.RawUI.WindowTitle = "$filenameScript $strResult"
echo;}
echo;
echo;function EoF^($timePause^) {
echo;  Start-Sleep -milliseconds $timePause
echo;}
echo;
echo;ChDirWork $Args[0]
echo;$strClip = GetClip
echo;$numLineClip = ViewClip $strClip
echo;DivText $strClip $numLineClip $filenameScript $extLog
echo;EoF $timePause
echo;
echo;--------------------------------------------------------------------------
echo;
echo;「クリップボードに送る内容」
echo;
echo;↓↓↓↓↓↓↓↓
)                     >  "%~dp0メール本文.txt"

type "%ARC_File_TXT%" >> "%~dp0メール本文.txt"

rem /;
rem /; ◆ 生成されたメール本文または添付ファイルをクリップボードへ送る
rem /;

for /f "usebackq tokens=* delims=" %%0 in (`call CSCRIPT //NOLOGO "%~dp0③MSGBOX.VBS" "★ クリップボードに送る内容を選択して下さいcrlfcrlf  【 はい 】     アプリとデータcrlfcrlf  【 いいえ 】     データのみcrlfcrlf  【 キャンセル 】  送らないcrlfcrlf"    259 "クリップボード設定"`) do SET 答え=%%0
if      "%答え%"=="Yes"     type                     "%~dp0メール本文.txt" | clip
if      "%答え%"=="No"      type                     "%ARC_File_TXT%"      | clip

0
0
0

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
0
0