Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/csharp/284.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
gmail api发送邮件无法运行C#控制台应用程序(身份验证范围不足)_C#_.net_Google Cloud Platform_Gmail Api - Fatal编程技术网

gmail api发送邮件无法运行C#控制台应用程序(身份验证范围不足)

gmail api发送邮件无法运行C#控制台应用程序(身份验证范围不足),c#,.net,google-cloud-platform,gmail-api,C#,.net,Google Cloud Platform,Gmail Api,我是谷歌云/gmail API新手。在c#中,我想使用他们的gmail api: 登录谷歌云-works 阅读列表项目-作品 发送电子邮件-不起作用 步骤3中的Api返回请求范围不足(403)我有信心登录到我的云帐户:我最怀疑的代码是: static string[] Scopes = { GmailService.Scope.GmailAddonsCurrentActionCompose, GmailService.Scope.GmailAddonsCurrentMessageAction

我是谷歌云/gmail API新手。在c#中,我想使用他们的gmail api:

  • 登录谷歌云-works
  • 阅读列表项目-作品
  • 发送电子邮件-不起作用
  • 步骤3中的Api返回请求范围不足(403)我有信心登录到我的云帐户:我最怀疑的代码是:

     static string[] Scopes = { GmailService.Scope.GmailAddonsCurrentActionCompose, GmailService.Scope.GmailAddonsCurrentMessageAction };
    
    我得到了这个错误

     Request had insufficient authentication scopes. [403]
    Errors [
            Message[Insufficient Permission] Location[ - ] Reason[insufficientPermissions] Domain[global]
    ]
    
    //代码

     class Program
    {
        // If modifying these scopes, delete your previously saved credentials
        // at ~/.credentials/gmail-dotnet-quickstart.json
        static string[] Scopes = { GmailService.Scope.GmailAddonsCurrentActionCompose, GmailService.Scope.GmailAddonsCurrentMessageAction };
        static string ApplicationName = "Gmail API .NET Quickstart";
        static void Main(string[] args)
        {
            UserCredential credential;
            using (var stream =
                new FileStream("credentials.json", FileMode.Open, FileAccess.Read))
            {
                // The file token.json stores the user's access and refresh tokens, and is created
                // automatically when the authorization flow completes for the first time.
                string credPath = "token.json";
                credential = GoogleWebAuthorizationBroker.AuthorizeAsync(
                    GoogleClientSecrets.Load(stream).Secrets,
                    Scopes,
                    "user",
                    CancellationToken.None,
                    new FileDataStore(credPath, true)).Result;
                Console.WriteLine("Credential file saved to: " + credPath);
            }
            // Create Gmail API service.
            var service = new GmailService(new BaseClientService.Initializer()
            {
                HttpClientInitializer = credential,
                ApplicationName = ApplicationName,
            });
            // Define parameters of request.
            UsersResource.LabelsResource.ListRequest request = service.Users.Labels.List("me");
            // List labels.
            IList<Label> labels = request.Execute().Labels;
            Console.WriteLine("Labels:");
            if (labels != null && labels.Count > 0)
            {
                foreach (var labelItem in labels)
                {
                    Console.WriteLine("{0}", labelItem.Name);
                }
            }
            else
            {
                Console.WriteLine("No labels found.");
            }
            string plainText = "Body Test";
            var newMsg = new Google.Apis.Gmail.v1.Data.Message();
            newMsg.Raw = Program.Base64UrlEncode(plainText.ToString());
            try
            {
                service.Users.Messages.Send(newMsg, "me").Execute();
            }
            catch (Exception ex)
            {
                Console.WriteLine(ex.Message);
            }
            /*
             {"Google.Apis.Requests.RequestError\r\nRequest had insufficient authentication scopes. 
              [403]\r\nErrors [\r\n\tMessage[Insufficient Permission] Location[ - ] Reason[insufficientPermissions] Domain[global]\r\n]\r\n"}   Google.GoogleApiException
             */
            Console.Read();
        }
        public static string Base64UrlEncode(string input)
        {
            var inputBytes = System.Text.Encoding.UTF8.GetBytes(input);
            return Convert.ToBase64String(inputBytes).Replace("+", "-").Replace("/", "_").Replace("=", "");
        }
    }
    
    好: 我决定将GMAIL.API提供的凭证文件放入单行环境变量中,并将JSON转换为GoogleClientSecrets:

        private static GoogleClientSecrets GetSecretsFromEnvironment()
        {
            var environmentConfiguration = new ConfigurationBuilder()
                .AddEnvironmentVariables()
                .Build();   
            var secretsEnv = environmentConfiguration["GoogleSecrets"];
            var secrets = JsonConvert.DeserializeObject<GoogleClientSecrets>(secretsEnv);
            return secrets;
        }
    
    private static GoogleClientSecrets GetSecretsFromEnvironment()
    {
    var environmentConfiguration=new ConfigurationBuilder()
    .AddenEnvironmentVariables()
    .Build();
    var secretsEnv=environmentConfiguration[“GoogleSecrets”];
    var secrets=JsonConvert.DeserializeObject(secretsEnv);
    归还机密;
    }
    
    appsettings.json

    {
      "MailSettings": {
        "account": "mark.d.wardell@gmail.com",
        "subject": "Please Confirm Account",
        "from": "mark.d.wardell@gmail.com",
        "HTML": "<b>Hello {0}</b>"
      }
    }
    
    {
    “邮件设置”:{
    “账户”:“mark.d。wardell@gmail.com",
    “主题”:“请确认账户”,
    “from”:“mark.d。wardell@gmail.com",
    HTML:“你好{0}”
    }
    }
    
    由google云控制台提供的credentials.json。我生成了一个单行字符串并添加到EnvironmentVariable

    以及呼叫代码:

    using Google.Apis.Auth.OAuth2;
    using Google.Apis.Gmail.v1;
    using Google.Apis.Services;
    using Google.Apis.Util.Store;
    using Microsoft.Extensions.Configuration;
    using Newtonsoft.Json;
    using System;
    using System.Collections.Generic;
    using System.IO;
    using System.Linq;
    using System.Net.Mail;
    using System.Threading;
    using System.Threading.Tasks;
    namespace SendMail
    {
        class Program
        {
            // If modifying these scopes, delete your previously saved credentials
            // at ~/.credentials/gmail-dotnet-quickstart.json
            static string[] Scopes = { GmailService.Scope.GmailAddonsCurrentActionCompose, GmailService.Scope.GmailAddonsCurrentMessageAction, GmailService.Scope.GmailSend };
            static string ApplicationName = "Restful Resting Place";
            static async Task Main(params string[] args)
            {
                try
                {
                    var configuration = new ConfigurationBuilder()
                        .AddJsonFile("appsettings.json")
                        .Build();
                    Dictionary<string, string> MailSettings;
                    MailSettings = configuration.GetSection("MailSettings").GetChildren().ToDictionary(x => x.Key, x => x.Value);
                    MailSettings.Add("to", args[0]);
                    MailSettings.Add("link", args[1]);
                    GoogleClientSecrets gSecrets = GetSecretsFromEnvironment();
                    string credPath = "token.json";
                    UserCredential gcredential = await GoogleWebAuthorizationBroker.AuthorizeAsync(
                           gSecrets.Secrets,
                           Scopes,
                           MailSettings["account"],
                           CancellationToken.None,
                           new FileDataStore(credPath, true));
                    var service = new GmailService(new BaseClientService.Initializer()
                    {
                        HttpClientInitializer = gcredential,
                        ApplicationName = ApplicationName,
                    });
    
                    SendItTwo(service, MailSettings);
                    Console.WriteLine()
                }catch (Exception ex)
                {
                    Console.WriteLine(ex.Message);
                }   
            }
            private static GoogleClientSecrets GetSecretsFromEnvironment()
            {
                var environmentConfiguration = new ConfigurationBuilder()
                    .AddEnvironmentVariables()
                    .Build();   
                var secretsEnv = environmentConfiguration["GoogleSecrets"];
                var secrets = JsonConvert.DeserializeObject<GoogleClientSecrets>(secretsEnv);
                return secrets;
            }
            public static void SendItTwo(GmailService gmail,   Dictionary<string,string> dict)
            {
                MailMessage mailmsg = new MailMessage();
                {
                    mailmsg.Subject = dict["subject"];
                    mailmsg.Body = string.Format(dict["HTML"],dict["link"]);
                    mailmsg.From = new MailAddress(dict["from"]);
                    mailmsg.To.Add(new MailAddress(dict["to"]));         
                    mailmsg.IsBodyHtml = true;
                }
    
                ////add attachment if specified
                if (dict.ContainsKey("attachement"))
                {
                    if (File.Exists(dict["attachment"]))
                    {
                        Attachment data = new Attachment(dict["attachment"]);
                        mailmsg.Attachments.Add(data);
    
                    }else
                    {
                        Console.WriteLine("Error: Invalid Attachemnt");
                    }
                }     
                //Make mail message a Mime message
                MimeKit.MimeMessage mimemessage = MimeKit.MimeMessage.CreateFromMailMessage(mailmsg);
                Google.Apis.Gmail.v1.Data.Message finalmessage = new Google.Apis.Gmail.v1.Data.Message();
                finalmessage.Raw = Base64UrlEncode(mimemessage.ToString());  
                var result = gmail.Users.Messages.Send(finalmessage, "me").Execute();
            } 
            public static string Base64UrlEncode(string input)
            {
                var inputBytes = System.Text.Encoding.UTF8.GetBytes(input);
                return Convert.ToBase64String(inputBytes).Replace("+", "-").Replace("/", "_").Replace("=", "");
            }
        }
    }
    
    使用Google.api.Auth.OAuth2;
    使用Google.api.Gmail.v1;
    使用Google.api.Services;
    使用Google.api.Util.Store;
    使用Microsoft.Extensions.Configuration;
    使用Newtonsoft.Json;
    使用制度;
    使用System.Collections.Generic;
    使用System.IO;
    使用System.Linq;
    使用System.Net.Mail;
    使用系统线程;
    使用System.Threading.Tasks;
    名称空间SendMail
    {
    班级计划
    {
    //如果修改这些作用域,请删除以前保存的凭据
    //位于~/.credentials/gmail-dotnet-quickstart.json
    静态字符串[]Scopes={GmailService.Scope.gmailddonscurrentactioncompose,GmailService.Scope.gmailddonscurrentMessageAction,GmailService.Scope.GmailSend};
    静态字符串ApplicationName=“Restful rest-Place”;
    静态异步任务主(参数字符串[]args)
    {
    尝试
    {
    var configuration=new ConfigurationBuilder()
    .AddJsonFile(“appsettings.json”)
    .Build();
    字典设置;
    MailSettings=configuration.GetSection(“MailSettings”).GetChildren().ToDictionary(x=>x.Key,x=>x.Value);
    MailSettings.Add(“to”,args[0]);
    MailSettings.Add(“link”,args[1]);
    GoogleClientSecrets gSecrets=GetSecretsFromEnvironment();
    字符串credPath=“token.json”;
    UserCredential gcredential=等待GoogleWebAuthorizationBroker.AuthorizationAsync(
    秘密,秘密,
    范围,
    邮件设置[“帐户”],
    取消令牌。无,
    新文件数据存储(credPath,true));
    var service=new-GmailService(new-BaseClientService.Initializer()
    {
    HttpClientInitializer=gcredential,
    ApplicationName=ApplicationName,
    });
    SendItTwo(服务、邮件设置);
    Console.WriteLine()
    }捕获(例外情况除外)
    {
    控制台写入线(例如消息);
    }   
    }
    私有静态GoogleClientSecrets GetSecretsFromenEnvironment()
    {
    var environmentConfiguration=new ConfigurationBuilder()
    .AddenEnvironmentVariables()
    .Build();
    var secretsEnv=environmentConfiguration[“GoogleSecrets”];
    var secrets=JsonConvert.DeserializeObject(secretsEnv);
    归还机密;
    }
    公共静态void SendItTwo(gmail服务gmail,字典dict)
    {
    MailMessage mailmsg=新邮件();
    {
    mailmsg.Subject=dict[“Subject”];
    mailmsg.Body=string.Format(dict[“HTML”]、dict[“link”]);
    mailmsg.From=新邮件地址(dict[“From”]);
    mailmsg.To.Add(新邮件地址(dict[“To”]);
    mailmsg.IsBodyHtml=true;
    }
    ////如果指定,请添加附件
    如果(附件)
    {
    如果(文件.Exists(dict[“附件”]))
    {
    附件数据=新附件(dict[“附件]);
    mailmsg.Attachments.Add(数据);
    }否则
    {
    Console.WriteLine(“错误:无效附件”);
    }
    }     
    //将邮件消息设置为Mime消息
    MimeKit.MimeMessage MimeMessage=MimeKit.MimeMessage.CreateFromMailMessage(mailmsg);
    Google.api.Gmail.v1.Data.Message finalmessage=new Google.api.Gmail.v1.Data.Message();
    finalmessage.Raw=Base64UrlEncode(mimessage.ToString());
    var result=gmail.Users.Messages.Send(finalmessage,“me”).Execute();
    } 
    公共静态字符串Base64UrlEncode(字符串输入)
    {
    var inputBytes=System.Text.Encoding.UTF8.GetBytes(输入);
    返回Convert.ToBase64String(inputBytes)。替换(“+”,“-”)。替换(“/”,“”)。替换(“=”,”);
    }
    }
    }
    
    好的: 我决定将GMAIL.API提供的凭证文件放入单行环境变量中,并将JSON转换为GoogleClientSecrets:

        private static GoogleClientSecrets GetSecretsFromEnvironment()
        {
            var environmentConfiguration = new ConfigurationBuilder()
                .AddEnvironmentVariables()
                .Build();   
            var secretsEnv = environmentConfiguration["GoogleSecrets"];
            var secrets = JsonConvert.DeserializeObject<GoogleClientSecrets>(secretsEnv);
            return secrets;
        }
    
    private static GoogleClientSecrets GetSecretsFromEnvironment()
    {
    var environmentConfiguration=new ConfigurationBuilder()
    .AddenEnvironmentVariables()
    .Build();