はっきり言って面倒なやり方です。
手間を惜しまず、パスワード付き 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 が
送信準備-①で作成した作業用フォルダに作成される
ファイルの選択後、クリップボードに送る内容を選択
アプリとデータを送る場合は、【 はい 】をクリック
データのみを送る場合は、【 いいえ 】をクリック
クリップボードに送らない場合は、【 キャンセル 】をクリック
送信先の復元環境が用意されていない場合は
アプリとデータを送って下さい。
送信処理-④ クリップボードの中身をメール本文に貼付後、送信
※ Gmail の場合、サイズが大きいと処理落ちするので
メール本文.txt をメモ帳で開き
先頭のアプリの部分を一度貼付けてから
残りを貼付けると成功しました。
受信側の作業
復元準備-① 作業フォルダを作成してメール本文の復元アプリを保存
● 作業用のフォルダを作り
「①復元するアプリ【★ダブルクリックするのはコレ★】.bat」 と
「②復元するアプリ.ps1」
を同じフォルダにファイルを作成して
文字コード を ANSI で保存する
復元処理-② メール本文の添付ファイルを復元
● メール本文の「↓↓↓↓↓↓↓↓」の
次の行から -----END CERTIFICATE-----
までをクリップボードにコピーする
下記の例の場合
「クリップボードに送る内容」
↓↓↓↓↓↓↓↓
添付.zip
-----BEGIN CERTIFICATE-----
r2J3btgBxX2vYndu2AFQSwUGAAAAAAEAAQByAAAAXAAAAAAA
-----END CERTIFICATE-----
の 添付.zip から 4行を選択して、
右クリックメニューでコピーする
● 「①復元するアプリ【★ダブルクリックするのはコレ★】.bat」 を ダブルクリックで実行
上記の例の場合、作業用のフォルダに 添付.zip が作成される
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 {
'未選択'
}
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
@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