質問をすることでしか得られない、回答やアドバイスがある。

15分調べてもわからないことは、質問しよう!

新規登録して質問してみよう
ただいま回答率
85.50%
VBA

VBAはオブジェクト指向プログラミング言語のひとつで、マクロを作成によりExcelなどのOffice業務を自動化することができます。

Q&A

解決済

1回答

3796閲覧

Outlookで開いているメールの添付ファイルの中で、任意の文字列を含むファイルのみ、所定のフォルダに保存するマクロを組みたい

Crucian_carp

総合スコア11

VBA

VBAはオブジェクト指向プログラミング言語のひとつで、マクロを作成によりExcelなどのOffice業務を自動化することができます。

0グッド

0クリップ

投稿2020/04/16 13:35

前提・実現したいこと

Outlookで受信したメールから、特定の文字列"○○○yymm.xlsx"(〇=アルファベット3文字)というファイル名の添付ファイルを所定のフォルダに保存するようなマクロを組みたいです。
"yymm"のところをワイルドカードにして書いているのですが、その行でエラーが発生してしまいます。

発生している問題・エラーメッセージ

実行時エラー”5” プロシージャの呼び出し、または引数が不正です。

該当のソースコード

Sub SaveAttachmentFile2() Dim objItem As Object Dim strfile As String Dim strPath As String strPath = "C:\Users\Atsuki\Desktop\新しいフォルダー (2)\" 'ファイルを保存したいフォルダ Set objItem = Application.ActiveInspector.CurrentItem '今開いているメールオブジェクトを取得 With objItem If Not .Attachments.Item.FileName Like "DRF####.xlsx" Then Exit Sub Else strfile = strPath & .Attachments.Item.FileName Like ("DRF####") .Attachments.Item.SaveAsFile strfile End If End With

試したこと

さまざまなサイトを参考にしたのですが、私と同じ目的のマクロを組まれた方の事例が見当たりませんでした。
実行時エラー"5"は、関数の引数が間違っている際に表示されるエラーとのことですが、何が間違っているのかわかりません…お手数おかけしますが、何卒よろしくお願いいたします。

補足情報(FW/ツールのバージョンなど)

ここにより詳細な情報を記載してください。

気になる質問をクリップする

クリップした質問は、後からいつでもMYページで確認できます。

またクリップした質問に回答があった際、通知やメールを受け取ることができます。

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

meg_

2020/04/16 14:31

エラーが発生しているのはどの行ですか?
Crucian_carp

2020/04/16 14:33

ご質問ありがとうございます。エラーが発生しているのはIF NOTの行になります。
meg_

2020/04/16 14:42

Like "DRF####.xlsx"の部分は問題なさそうです。 .Attachments.Item.FileNameの問題ではないでしょうか?
Crucian_carp

2020/04/16 14:44

お返事ありがとうございます。私もfilenameの箇所が怪しいと思っております。しかし、その部分についてもなにが間違っているのか、どのように書き換えたらよいかわからず…
guest

回答1

0

ベストアンサー

.Attachments.Item.FileNameが問題の箇所です。

まず、AttachmentsプロパティはAttachment「s」とあるように、親要素(objItem)の添付ファイルの「集合」を示します。

添付ファイルの集合の中の要素(Item)を取得しようとしていますが、こ集合の中から一つを取り出すために、一意となる情報(集合の中での位置や名前)を指定する必要があります。

つまり、.Attachments.Item(1).FileNameなどのように、Itemメソッドに引数を渡す必要があります。


上記の
「~s」となっていれば要素の集合、
「~s」には集合の中の要素を一つ取り出すItem(Index)というプロパティやメソッドがある
という話は、Outlookに限らずVBAのほとんどのオブジェクトで言える話となります。

また、今回のコードでは以下のように型を明示することで、実行前にVBAが問題を指摘してくれます。

vba

1Dim objItem As Outlook.MailItem

イメージ説明

Outlookの要素には様々な種類があるため、型を固定すると上手く行かない場面もあるかと思いますが、処理を作る段階では型を明示してしまった方がやりやすいでしょう。


参考:For EachおよびFor Nextによる列挙

vba

1'Outlookで開いているメールの添付ファイルの中で、任意の文字列を含むファイルのみ、所定のフォルダに保存するマクロを組みたい 2'https://teratail.com/questions/254179 3Sub SaveAttachmentFile3() 4 5 'ファイルを保存したいフォルダ 6 Dim destFolderPath As String 7 destFolderPath = "C:\Users\Atsuki\Desktop\新しいフォルダー (2)\" 8 9 '今閲覧中のオブジェクトを取得(メールなど) 10 Dim objItem As Object 11 Set objItem = Application.ActiveInspector.CurrentItem 12 13 '保存するファイルのフルパス 14 Dim fullFileName As String 15 16 'For Each の場合 17 Dim at As Outlook.Attachment 18 For Each at In objItem.Attachments 19 Debug.Print at.FileName 20 21 If at.FileName Like "DRF####.xlsx" Then 22 23 fullFileName = destFolderPath & at.FileName 24 25 'at.SaveAsFile fullFileName 26 End If 27 Next at 28 29 30 'For Next の場合 31 With objItem.Attachments 32 33 Dim i As Long 34 For i = 1 To .Count 35 Debug.Print .Item(i).FileName 36 37 If .Item(i).FileName Like "DRF####.xlsx" Then 38 39 40 fullFileName = destFolderPath & .Item(i).FileName 41 42 '.Item(i).SaveAsFile fullFileName 43 End If 44 Next i 45 46 End With 'objItem.Attachments 47End Sub

投稿2020/04/16 23:02

編集2020/04/17 09:28
imihito

総合スコア2166

バッドをするには、ログインかつ

こちらの条件を満たす必要があります。

Crucian_carp

2020/04/17 00:41

imihitoさま 御回答いただきありがとうございました。 間違っていた原因が非常によく理解できました。 申し訳ないのですが、追加で質問させていただきたいのですが Itemメソッドで(1)のようにIndexを指定してしまうと、 もしそのファイルが2番目や3番目にあった場合にはうまく動作しないということにならないでしょうか。 この場合でもFileName Like ("DRF####")の情報を基に対象のファイルを見つけてくれるのでしょうか。 素人発想で申し訳ないのですが、Index番号を変数にしてしまいFor~Nextを組み込めばうまくいきそうな気がするのですが、考え間違っておりましたらご指摘いただけますと幸いです。 お手数おかけしますが、何卒よろしくお願いいたします。
imihito

2020/04/17 09:15

> Itemメソッドで(1)のようにIndexを指定してしまうと、 もしそのファイルが2番目や3番目にあった場合にはうまく動作しないということにならないでしょうか。 その通りです。 対処も書かれているとおりで、For~NextやFor Eachを使えば大丈夫なはずです。 (個人的にはコードがすっきりとしやすいFor Eachの方が好みです)
Crucian_carp

2020/04/18 03:49

imihitoさま 回答と解説、誠にありがとうございました。 先ほど確認させていただきましたが、やりたいと思っていた動作が行われていることを確認できました。 お手数おかけしてもうしけないのですが、もしよろしければ追加で質問させていただいてもよろしいでしょうか。 imihitoさまが”参考”にて書いていただいたVBAの”Dim at As Outlook.Attachment”の箇所の”Outlook.Attachment”の部分なのですが、 Outlookアプリケーションオブジェクトのすぐ後にAttachmentオブジェクトを持ってこれるという認識がありませんでした。(”ActiveInspector.CurrentItem”を挟まなければいけないと思っていました。)が、このようなこともできるのでしょうか。 Officeデベロッパーセンター(https://docs.microsoft.com/ja-jp/office/vba/api/outlook.application)には3つほどOutlookアプリケーションオブジェックトのできることが記されていますが、このうちのどの機能が該当するのでしょうか。 もし、可能でしたら教えていただけますと幸甚に存じます。 よろしくお願いいたします。
imihito

2020/04/18 06:59

`As`の後ろに書かれているのは、実体のあるオブジェクトへの参照ではなく、型を示すものになります。 「ツール(T)」の「参照設定(R)...」に「Microsoft Outlook XX.0 Object Library」(XXは数値)というライブラリが含まれていると思いますが、 このライブラリは、VBAのコード中では「Outlook」という識別子で示されます(オブジェクトブラウザを見ることで確認できます)。 つまり、`Dim at As Outlook.Attachment`というステートメントは `at`という名前の変数を宣言します。その型は「Outlook」という識別子で示されるライブラリの中の、「Attachment」という型です。 という意味になります。 型を指定するときのライブラリ名は省略可能であり、参照設定が少なければ問題になることも少ないですが、「何を操作しているコードなのか?」を明示するために私は付けています。 なお、省略時に問題になる例としては、複数のライブラリに同じ名前の型が含まれる場合があります。 例えば、OutlookにもExcelにも「Application」という型は存在しますが、普通に「~ As Application」と記述すると、どちらの型を示すのかは「参照設定」を見ないとわかりません。 このとき、「~ As Outlook.Application」や「~ As Excel.Application」と記述することで、型の名前があいまいな場合でも意図した型を指定できます。
Crucian_carp

2020/04/18 07:12

imihitoさま お返事ありがとうございます。 理解できました。 これまで私が見てきた変数の宣言においてはライブラリ名が全て省略されていたのですね。 初心者の私に優しく丁寧に教えていただき、本当にありがとうございました!
guest

あなたの回答

tips

太字

斜体

打ち消し線

見出し

引用テキストの挿入

コードの挿入

リンクの挿入

リストの挿入

番号リストの挿入

表の挿入

水平線の挿入

プレビュー

15分調べてもわからないことは
teratailで質問しよう!

ただいまの回答率
85.50%

質問をまとめることで
思考を整理して素早く解決

テンプレート機能で
簡単に質問をまとめる

質問する

関連した質問