Netcore 2.2 - Docker Container cannot sending mail - c#

i'm current deploy one application into docker container, this app have function sending mail
(base on c# netcore 2.2)
but i can not sending mail (while mean i can sending mail from localhost)
the message of exception in docker
System.ComponentModel.Win32Exception: GSSAPI operation failed with
error - Unspecified GSS failure. Minor code may provide more
information (Cannot find KDC for realm "xxx.yyyy"). at
System.Net.Security.NegotiateStreamPal.AcquireCredentialsHandle(String
package, Boolean isServer, NetworkCredential credential) at
System.Net.NTAuthentication.Initialize(Boolean isServer, String
package, NetworkCredential credential, String spn, ContextFlagsPal
requestedContextFlags, ChannelBinding channelBinding) at
System.Net.Mail.SmtpNegotiateAuthenticationModule.Authenticate(String
challenge, NetworkCredential credential, Object sessionCookie, String
spn, ChannelBinding channelBindingToken) at
System.Net.Mail.SmtpConnection.SetContextAndTryAuthenticate(ISmtpAuthenticationModule
module, NetworkCredential credential, ContextAwareResult context)
at System.Net.Mail.SmtpConnection.GetConnection(String host, Int32
port) at System.Net.Mail.SmtpTransport.GetConnection(String host,
Int32 port) at System.Net.Mail.SmtpClient.GetConnection() at
System.Net.Mail.SmtpClient.Send(MailMessage message) --- End of
inner exception stack trace --- at
System.Net.Mail.SmtpClient.Send(MailMessage message)
i have try some help from google but can not, so please help me
thanks

It seems there is an issue in dotnet on linux, when you send mails with the GSSAPI authentication type:
https://github.com/dotnet/runtime/issues/2174, https://github.com/dotnet/runtime/issues/25885, https://github.com/dotnet/runtime/issues/27285
Try installing "gss-ntlmssp" in the container if you need to use GSSAPI.
Or, if your server accepts other authentication types, use another one, like NTLM:
var cred = new NetworkCredential(user, password, domain);
var cache = new CredentialCache();
cache.Add(host, 25, "NTLM", cred);
client.Credentials = cache;

Related

Cannot send email from an ASP.NET 4.8 website in prod

I created an ASP.NET website using C# that targets .NET 4.8 using Visual Studio.
The website is hosted at Ionos (aka 1&1) on a Windows Server, but I have no access to it or to the IIS console.
From my dev workstation, I can successfully send emails using MailSender.Send(....) define in the following code:
using System;
using System.Net;
using System.Net.Mail;
public class MailSender {
public static void Send(string server, int port, string body, string subject, string to = "xxxxxxx#gmail.com", string from = "noreply#xxxxxxxx.com") {
ServicePointManager.SecurityProtocol = SecurityProtocolType.Tls12;
SmtpClient smtp = new SmtpClient(server, port);
smtp.Credentials = new NetworkCredential(user, pw);
smtp.EnableSsl = true;
MailMessage Msg = new MailMessage();
Msg.From = new MailAddress(from);
Msg.To.Add(to);
Msg.Subject = subject;
Msg.IsBodyHtml = true;
Msg.Body = BuildBody(body);
smtp.Send(Msg);
}
}
Nevertheless, when the exact same website is put on the host server, this fails with following error:
System.Net.Mail.SmtpException: Failure sending mail. ---> **System.IO.IOException: Unable to read data from the transport connection: net_io_connectionclosed**.
at System.Net.Mail.SmtpReplyReaderFactory.ProcessRead(Byte[] buffer, Int32 offset, Int32 read, Boolean readLine)
at System.Net.Mail.SmtpReplyReaderFactory.ReadLines(SmtpReplyReader caller, Boolean oneLine)
at System.Net.Mail.SmtpReplyReaderFactory.ReadLine(SmtpReplyReader caller)
at System.Net.Mail.SmtpConnection.GetConnection(ServicePoint servicePoint)
at System.Net.Mail.SmtpTransport.GetConnection(ServicePoint servicePoint)
at System.Net.Mail.SmtpClient.GetConnection()
at System.Net.Mail.SmtpClient.Send(MailMessage message) --- End of inner exception stack trace ---
at System.Net.Mail.SmtpClient.Send(MailMessage message)
at MailSender.Send_New(String server, Int32 port, String body, String subject, String to, String from)
Could anyone give me a hint on what I can do to fix this?
What I tried, so far:
Port I use is now 587, but 465 or 25 give the same result.
I tried several SecurityProtocolType values, with no difference.
I tried many different ways of sending (System.Web.Mail, built-in WebMail class, etc...) with same result.
I also checked that my website actually targets .NET 4.8
Searching, I found many articles on Google and dev forums, with many tips, but nothing seems to help in my very case
I also contacted Ionos support, who seem to say they have no problem and that this is a dev problem, so they cannot help...
Now I definitely need help, because it's now more than 2 weeks I'm trying things with no succes :(
Thanks in advance for any help!!

ASP.NET receives post data issue

I used ASP.NET to write a web page that accesses other websites to log in to the API, and it was successfully placed on my server, but when it was placed on the school's server to receive the token from the post, the following error was reported:
Server Error in '/classMeeting' Application. A connection attempt failed because the connecting party did not properly reply after a period of time or the connected host became unresponsive. 112.65.235.59:443
Description: An unhandled exception occurred during the execution of the current web request.
Please review the stack trace for more information about the error and where it originated in the code.
Exception Details:
System.Net.Sockets.SocketException:
A connection attempt failed because the connected party did not properly reply after a period of time or the connected host became unresponsive. 112.65.235.59:443
Source Error:
An unhandled exception was generated during the execution of the current webrequest. Information regarding the origin and location of the exception can be identified using the exception stack trace below.
System.Net.Sockets.Socket.DoConnect(EndPoint endPointSnapshot, SocketAddress socketAddress) +309
System.Net.ServicePoint.ConnectSocketInternal(Boolean connectFailure, Socket s4, Socket s6, Socket& socket, IPAddress& address, ConnectSocketState state, IAsyncResult asyncResult, Exception& exception) +633
System.Net.HttpWebRequest.GetRequestStream(TransportContext& context) +708
System.Net.HttpWebRequest.GetRequestStream() +21
classMeeting.index.GetAccess_token(String code, String client_id, String redirect_uri, String client_secret) in C:\Users\admin\source\repos\classMeeting\index.aspx.cs:130 classMeeting.index.readyLogin() in C:\Users\admin\source\repos\classMeeting\index.aspx.cs:32
classMeeting.index.Page_Load(Object sender, EventArgs e) in C:\Users\admin\source\repos\classMeeting\index.aspx.cs:25
System.Web.UI.Control.OnLoad(EventArgs e) +109
System.Web.UI.Control.LoadRecursive() +68
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +3321
My source code is:
public static string GetAccess_token(string code, string client_id, string redirect_uri, string client_secret)
{
var url = "https://openapi.yiban.cn/oauth/access_token";
byte[] byteArray = Encoding.UTF8.GetBytes(string.Format("client_id={0}&client_secret={1}&code={2}&redirect_uri={3}", client_id, client_secret, code, redirect_uri));
HttpWebRequest webRequest = (HttpWebRequest)WebRequest.Create(new Uri(url));
webRequest.Method = "Post";
webRequest.ContentType = "application/x-www-form-urlencoded";
webRequest.ContentLength = byteArray.Length;
ServicePointManager.DefaultConnectionLimit = 50;
Stream newStream = webRequest.GetRequestStream();
newStream.Write(byteArray, 0, byteArray.Length);
newStream.Close();
HttpWebResponse response = (HttpWebResponse)webRequest.GetResponse();
StreamReader php = new StreamReader(response.GetResponseStream(), Encoding.Default);
return php.ReadToEnd();
}
How should we do to fix this error?
If you get any error code like 10036 for a socket connection error then you can find the related error section from this link
Check the parameters you use for connection like hostname and port, and also make sure your firewall doesn't drop packages or block your connection.
The code you provided is correct, there are several reasons for this phenomenon:
Check whether the status of the server is abnormal. For example, there may be a state of not starting or being paralyzed.
Whether the status of your destination URL is normal. Whether there is an unreachable state.
Whether your server can access your target website. Due to the server's need for a secure environment, there are usually some URLs that cannot be accessed by the server. At this point you need to change your server port. If it still doesn't work, try sending and receiving web requests to hosts that it can access successfully.

Grpc.Core.RpcException when calling gRPC service from .NET MAUI app

I have developed a simple ASP .NET 6 backend server that provides services over gRPC. I also wrote a basic WPF Desktop application and a simple .NET MAUI app (configured for Android devices) as client applications.
I started my services like this below:
public static IHostBuilder CreateHostBuilder(string[] args)
{
var configuration = ServiceFactory.Instance.GetConfiguration();
return Host.CreateDefaultBuilder(args).ConfigureWebHostDefaults(webBuilder =>
{
webBuilder.ConfigureKestrel(options =>
{
options.Listen(configuration.IPAddress, configuration.HttpPort);
options.Listen(configuration.IPAddress, configuration.HttpsPort, configure => configure.UseHttps());
});
webBuilder.UseStartup<Startup>();
});
}
The server application starts beautifully.
Desktop client works
When I start my WPF Desktop application, I use the following code to connect to the server and run the most basic service function: Ping. It is a function that always returns with a valid response object and it serves as a test if the server is alive and I can also test if general service calls work.
_grpcChannel = GrpcChannel.ForAddress("https://127.0.0.1:5005/", new GrpcChannelOptions()
{
MaxReceiveMessageSize = 16 * 1024 * 1024,
MaxSendMessageSize = 16 * 1024 * 1024,
HttpHandler = new HttpClientHandler
{
ServerCertificateCustomValidationCallback = HttpClientHandler.DangerousAcceptAnyServerCertificateValidator
}
});
_authenticationClient = new AuthenticationClient(_grpcChannel);
_authenticationClient.Ping(new PingRequest());
Mobile client does not work
This works exactly as expected. However, when I use the code below inside my .NET MAUI app, it fails.
_grpcChannel = GrpcChannel.ForAddress("http://127.0.0.1:5000/", new GrpcChannelOptions()
{
MaxReceiveMessageSize = 16 * 1024 * 1024,
MaxSendMessageSize = 16 * 1024 * 1024
});
_authenticationClient = new AuthenticationClient(_grpcChannel);
_authenticationClient.Ping(new PingRequest());
I use HTTP instead of HTTPS, because there is apparently an issue with HTTPS without valid SSL certificate, e.g. when you test locally. I have read this here.
Creating the gRPC channel does work in my .NET MAUI app and I can also create an instance of my AuthenticationClient. However, when I call the Ping service function I get this.
{Grpc.Core.RpcException: Status(StatusCode="Unavailable", Detail="Error connecting to subchannel.", DebugException="System.Net.Sockets.SocketException (111): Connection refused
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.ThrowException(SocketError error, CancellationToken cancellationToken)
at System.Net.Sockets.Socket.AwaitableSocketAsyncEventArgs.System.Threading.Tasks.Sources.IValueTaskSource.GetResult(Int16 token)
at System.Net.Sockets.Socket.<ConnectAsync>g__WaitForConnectWithCancellation|277_0(AwaitableSocketAsyncEventArgs saea, ValueTask connectTask, CancellationToken cancellationToken)
at Grpc.Net.Client.Balancer.Internal.SocketConnectivitySubchannelTransport.TryConnectAsync(ConnectContext context) in /_/src/Grpc.Net.Client/Balancer/Internal/SocketConnectivitySubchannelTransport.cs:line 140")
at Grpc.Net.Client.Balancer.Internal.ConnectionManager.PickAsync(PickContext context, Boolean waitForReady, CancellationToken cancellationToken) in /_/src/Grpc.Net.Client/Balancer/Internal/ConnectionManager.cs:line 352
at Grpc.Net.Client.Balancer.Internal.BalancerHttpHandler.SendAsync(HttpRequestMessage request, CancellationToken cancellationToken) in /_/src/Grpc.Net.Client/Balancer/Internal/BalancerHttpHandler.cs:line 109
at Grpc.Net.Client.Internal.GrpcCall`2.<RunCall>d__73[[Engine.Server.Contracts.PingRequest, Engine.Server.Contracts, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null],[Engine.Server.Contracts.PingResponse, Engine.Server.Contracts, Version=1.0.0.0, Culture=neutral, PublicKeyToken=null]].MoveNext() in /_/src/Grpc.Net.Client/Internal/GrpcCall.cs:line 493
at Grpc.Net.Client.Internal.HttpClientCallInvoker.BlockingUnaryCall[PingRequest,PingResponse](Method`2 method, String host, CallOptions options, PingRequest request) in /_/src/Grpc.Net.Client/Internal/HttpClientCallInvoker.cs:line 116
at Grpc.Core.Interceptors.InterceptingCallInvoker.<BlockingUnaryCall>b__3_0[PingRequest,PingResponse](PingRequest req, ClientInterceptorContext`2 ctx) in /_/src/Grpc.Core.Api/Interceptors/InterceptingCallInvoker.cs:line 51
at Grpc.Core.ClientBase.ClientBaseConfiguration.ClientBaseConfigurationInterceptor.BlockingUnaryCall[PingRequest,PingResponse](PingRequest request, ClientInterceptorContext`2 context, BlockingUnaryCallContinuation`2 continuation) in /_/src/Grpc.Core.Api/ClientBase.cs:line 174
at Grpc.Core.Interceptors.InterceptingCallInvoker.BlockingUnaryCall[PingRequest,PingResponse](Method`2 method, String host, CallOptions options, PingRequest request) in /_/src/Grpc.Core.Api/Interceptors/InterceptingCallInvoker.cs:line 48
at Engine.Server.Contracts.Authentication.AuthenticationClient.Ping(PingRequest request, CallOptions options) in [a path]\obj\Debug\net6.0\AuthenticationGrpc.cs:line 316
at Engine.Server.Contracts.Authentication.AuthenticationClient.Ping(PingRequest request, Metadata headers, Nullable`1 deadline, CancellationToken cancellationToken) in [a path]\obj\Debug\net6.0\AuthenticationGrpc.cs:line 306
Unfortunately, a web research did not reveal much and I am very new to .NET MAUI development. Any help is highly appreciated.
The correct answer was given by Jason as a comment to my original post. Although everything runs locally on my machine for testing, I need to provide the actual IP address in order to make it work for the Android emulator. Thank you, Jason.

Azure function exception - Error writing logs to table storage: Microsoft.Azure.Cosmos.Table.StorageException

I have an azure function that communicates with blob storage to read the last sync date time and then based on that, reading the data from the Cosmos database.
Few interactions work fine and randomly throwing the following exception in some cases
"Error writing logs to table storage:
Microsoft.Azure.Cosmos.Table.StorageException: An operation on a
socket could not be performed because the system lacked sufficient
buffer space or because a queue was full. --->
System.Net.Http.HttpRequestException: An operation on a socket could
not be performed because the system lacked sufficient buffer space or
because a queue was full. ---> System.Net.Sockets.SocketException
(10055): An operation on a socket could not be performed because the
system lacked sufficient buffer space or because a queue was full. at
System.Net.Http.ConnectHelper.ConnectAsync(String host, Int32 port,
CancellationToken cancellationToken) --- End of inner exception stack
trace --- at System.Net.Http.ConnectHelper.ConnectAsync(String host,
Int32 port, CancellationToken cancellationToken) at
System.Net.Http.HttpConnectionPool.ConnectAsync(HttpRequestMessage
request, Boolean allowHttp2, CancellationToken cancellationToken) at
System.Net.Http.HttpConnectionPool.CreateHttp11ConnectionAsync(HttpRequestMessage
request, CancellationToken cancellationToken) at
System.Net.Http.HttpConnectionPool.GetHttpConnectionAsync(HttpRequestMessage
request, CancellationToken cancellationToken) at
System.Net.Http.HttpConnectionPool.SendWithRetryAsync(HttpRequestMessage
request, Boolean doRequestAuth, CancellationToken cancellationToken)
at System.Net.Http.RedirectHandler.SendAsync(HttpRequestMessage
request, CancellationToken cancellationToken) at
System.Net.Http.DiagnosticsHandler.SendAsync(HttpRequestMessage
request, CancellationToken cancellationToken) at
System.Net.Http.HttpClient.FinishSendAsyncUnbuffered(Task1 sendTask, HttpRequestMessage request, CancellationTokenSource cts, Boolean disposeCts) at Microsoft.Azure.Cosmos.Table.RestExecutor.TableCommand.Executor.ExecuteAsync[T](RESTCommand1
cmd, IRetryPolicy policy, OperationContext operationContext,
CancellationToken token) --- End of inner exception stack trace --- at
Microsoft.Azure.Cosmos.Table.RestExecutor.TableCommand.Executor.ExecuteAsync[T](RESTCommand1 cmd, IRetryPolicy policy, OperationContext operationContext, CancellationToken token) at Microsoft.Azure.WebJobs.Logging.Utility.SafeExecuteAsync(CloudTable table, TableBatchOperation batch) in C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Logging\Internal\Utility.cs:line 178 at Microsoft.Azure.WebJobs.Logging.Utility.WriteBatchAsync[T](ILogTableProvider logTableProvider, IEnumerable1 e1) in
C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Logging\Internal\Utility.cs:line
268 at
Microsoft.Azure.WebJobs.Logging.LogWriter.FlushTimelineAggregateAsync(Boolean
always) in
C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Logging\Internal\LogWriter.cs:line
265 at Microsoft.Azure.WebJobs.Logging.LogWriter.FlushCoreAsync() in
C:\projects\azure-webjobs-sdk-rqm4t\src\Microsoft.Azure.WebJobs.Logging\Internal\LogWriter.cs:line
316 Request Information RequestID: RequestDate: StatusMessage:
ErrorCode:"
Can any one advise me how I can fix it?
I've just hit the same issue with a Function App I've just upgraded from v2 to v3.
As you note, the exception isn't from your code, but from within the Microsoft.Azure.WebJobs.Logging, which is just getting on with it's own thing regardless of what you're doing. It was also only happening locally, and not in my deployed instances.
Based on the answer here I deleted the AzureWebJobsDashboard setting from my local.settings.json file, and the error has gone away.
Internally Functions uses Table Storage for logging if the AzureWebJobsDashboard app setting is set. It's recommended to use Application Insights for logging in production scenarios, so you can safely remove this and set the APPINSIGHTS_INSTRUMENTATIONKEY app setting instead.
Seeing as I don't need logs stored for local development, and my deployed functions all only have the APPINSIGHTS_INSTRUMENTATIONKEY set.
Since you did not share any relevant piece of code from your function, my answer would be bit of generic. It seems to be due to socket exhaustion issue. While there is an inconclusive similar issue in github having some more details, a few good pointers to eliminate any low hanging fruits would be (I highly recommend you to read):
Manage connections in Azure Functions
Improper Instantiation antipattern
The major one I would particularly advise you to ensure shared connection reuse for Cosmos (or Table) client, HttpClient etc in a static private instance outside method.
Static clients
To avoid holding more connections than necessary, reuse client
instances rather than creating new ones with each function invocation.
We recommend reusing client connections for any language that you
might write your function in. For example, .NET clients like the
HttpClient,
DocumentClient,
and Azure Storage clients can manage connections if you use a single,
static client.
Here are some guidelines to follow when you're using a
service-specific client in an Azure Functions application:
Do not create a new client with every function invocation.
Do create a single, static client that every function invocation can use.
Consider creating a single, static client in a shared helper class if different functions use the same service.
Example:
using Microsoft.Azure.Documents.Client;
private static Lazy<DocumentClient> lazyClient = new Lazy<DocumentClient>(InitializeDocumentClient);
private static DocumentClient documentClient => lazyClient.Value;
private static DocumentClient InitializeDocumentClient()
{
// Perform any initialization here
var uri = new Uri("example");
var authKey = "authKey";
return new DocumentClient(uri, authKey);
}
// Function
public static async Task Run(string input)
{
Uri collectionUri = UriFactory.CreateDocumentCollectionUri("database", "collection");
object document = new { Data = "example" };
await documentClient.UpsertDocumentAsync(collectionUri, document);
// Rest of function
}

Windows Phone - failing to get a string from a website with login information

I am new to accessing web services with Windows Phone 7/8. I'm using a WebClient to get a string from a php-website. The site returns a JSON string but at the moment I'm just trying to put it into a TextBox as a normal string just to test if the connection works.
The php-page requires an authentication and I think that's where my code is failing. Here's my code:
WebClient client = new WebClient();
client.Credentials = new NetworkCredential("myUsername", "myPassword");
client.DownloadStringCompleted += new DownloadStringCompletedEventHandler(client_DownloadStringCompleted);
client.DownloadStringAsync(new Uri("https://www.mywebsite.com/ba/php/jsonstuff.php"));
void client_DownloadStringCompleted(object sender, DownloadStringCompletedEventArgs e)
{
try
{
string data = e.Result;
this.jsonText.Text = data;
}
catch (Exception ex)
{
System.Diagnostics.Debug.WriteLine(ex.Message);
}
}
This returns first a WebException and then a TargetInvocationException. If I replace the Uri with for example "http://www.google.com/index.html" the jsonText TextBox gets filled with html text from Google (oddly enough, this also works even when the WebClient credentials are still set).
So is the problem in the setting of the credentials? I couldn't find any good results when searching for guides on how to access php-pages with credentials, only without them. Then I found a short mention somewhere to use the WebClient.Credentials property. But should it work some other way?
Update: here's what I can get out of the WebException (sorry for the bad formatting):
System.Net.WebException: The remote server returned an error: NotFound. --->System.Net.WebException: The remote server returned an error: NotFound.
at System.Net.Browser.ClientHttpWebRequest.InternalEndGetResponse(IAsyncResult asyncResult)
at System.Net.Browser.ClientHttpWebRequest.<>c_DisplayClasse.b_d(Object sendState)
at System.Net.Browser.AsyncHelper.<>c_DisplayClass1.b_0(Object sendState)
--- End of inner exception stack trace ---
at System.Net.Browser.AsyncHelper.BeginOnUI(SendOrPostCallback beginMethod, Object state)
at System.Net.Browser.ClientHttpWebRequest.EndGetResponse(IAsyncResult asyncResult)
at System.Net.WebClient.GetWebResponse(WebRequest request, IAsyncResult result)
at System.Net.WebClient.DownloadBitsResponseCallback(IAsyncResult result)
Update 2: Here's the error log line:
Nov 16 17:51:12 myservice httpd[21036]: 127.0.0.1 - - [16/Nov/2012:17:51:12 +0200] "GET /ba/php/jsonstuff.php?origpath=/ba/php/jsonstuff.php HTTP/1.1" 401 290 "-" "Mozilla/5.0 (compatible; MSIE 10.0; Windows NT 6.2; WOW64; Trident/6.0)"
401 I guess would suggest false credentials?
In my opininion you really need to see how the server handles your request. "NotFound" in WebException could mean that you're referring to a location that doesn't exist. But I'm sure that you pass the right URL. So there must be some logic on the server that redirects you.
If you go to the url using your desktop browser - do you have any kind of SSL certificate error or warning? Maybe that's the reason. Try navigating on your phone using IE.
Or you could set up another host just to give it a try.
I'll set up a host on my machine and try it.
The problem is with the SSL certificate I guess. WP is very strict when it goes to checking SSL certificates, so you should try without ssl or install cert on your emulator/phone or install valid (not self generated) cert on your server.
Okay, so I found a way to get this working. The problem was that the WebClient class couldn't properly handle the cookies of the web service.
After some Google searches I found this solution and it works perfectly:
http://firebelly.net/post/3341374382/cookie-aware-webclient-for-wp7
So basically you just make your own client class that extends the WebClient class which can store cookies.

Categories