Neuron®
The Neuron® is the basis for the creation of open and secure federated networks for smart societies.
Loading...
Searching...
No Matches
Feedback.cs
1using System;
3using System.Net.Http;
4using System.Text;
5using System.Threading.Tasks;
6using Waher.Content;
8using Waher.Events;
12
14{
16 {
17 public Feedback()
18 : base("/Feedback")
19 {
20 }
21
22 public override bool HandlesSubPaths => false;
23 public override bool UserSessions => true;
24 public bool AllowsPOST => true;
25
26 public async Task POST(HttpRequest Request, HttpResponse Response)
27 {
28 if (!Request.HasData)
29 {
30 await Response.SendResponse(new BadRequestException());
31 return;
32 }
33
34 ContentResponse Content = await Request.DecodeDataAsync();
35 if (Content.HasError || !(Content.Decoded is Dictionary<string, string> Form))
36 {
37 await Response.SendResponse(new BadRequestException());
38 return;
39 }
40
41 string Name;
42 string EMail;
43 string Reason;
44 string Text;
45 string RecaptchaResponse;
46 bool ResponseDesired;
47
48 if (!Form.ContainsKey("Name") || string.IsNullOrEmpty(Name = Form["Name"]?.Trim()))
49 {
50 await Response.SendResponse(new BadRequestException());
51 return;
52 }
53
54 if (!Form.ContainsKey("EMail") || string.IsNullOrEmpty(EMail = Form["EMail"]?.Trim()))
55 {
56 await Response.SendResponse(new BadRequestException());
57 return;
58 }
59
60 if (!Form.ContainsKey("Reason") || string.IsNullOrEmpty(Reason = Form["Reason"]?.Trim()))
61 {
62 await Response.SendResponse(new BadRequestException());
63 return;
64 }
65
66 if (!Form.ContainsKey("Text") || string.IsNullOrEmpty(Text = Form["Text"]?.Trim()))
67 {
68 await Response.SendResponse(new BadRequestException());
69 return;
70 }
71
72 if (!Form.ContainsKey("g-recaptcha-response") || string.IsNullOrEmpty(RecaptchaResponse = Form["g-recaptcha-response"]))
73 {
74 await Response.SendResponse(new BadRequestException());
75 return;
76 }
77
78 if (!Form.ContainsKey("ResponseDesired"))
79 ResponseDesired = false;
80 else if (!CommonTypes.TryParse(Form["ResponseDesired"], out ResponseDesired))
81 {
82 await Response.SendResponse(new BadRequestException());
83 return;
84 }
85
86 if (await SiteVerify(RecaptchaResponse, Request.RemoteEndPoint))
87 {
88 KeyValuePair<string, object>[] Tags = await LoginAuditor.Annotate(Request.RemoteEndPoint,
89 new KeyValuePair<string, object>("Name", Name),
90 new KeyValuePair<string, object>("EMail", EMail),
91 new KeyValuePair<string, object>("Reason", Reason),
92 new KeyValuePair<string, object>("Text", Text),
93 new KeyValuePair<string, object>("ResponseDesired", ResponseDesired),
94 new KeyValuePair<string, object>("RemoteEndPoint", Request.RemoteEndPoint));
95
96 Dictionary<string, object> Feedback = new Dictionary<string, object>();
97 foreach (KeyValuePair<string, object> P in Tags)
98 Feedback.Add(P.Key, P.Value);
99
100 Request.Session["Feedback"] = Feedback;
101
102 StringBuilder Markdown = new StringBuilder();
103 DateTime Now = DateTime.Now;
104
105 Markdown.AppendLine("Feedback received.");
106 Markdown.AppendLine();
107
108 Markdown.AppendLine("| Feedback ||");
109 Markdown.AppendLine("|:------|:-------|");
110
111 Markdown.Append("| Name: | ");
112 Markdown.Append(MarkdownDocument.Encode(Name));
113 Markdown.AppendLine(" |");
114
115 Markdown.Append("| e-Mail: | <a href=\"mailto:");
116 Markdown.Append(EMail.Replace("\"", "&quot;"));
117 Markdown.Append("\" target=\"_blank\">");
118 Markdown.Append(MarkdownDocument.Encode(EMail));
119 Markdown.AppendLine("</a> |");
120
121 Markdown.Append("| Reason: | ");
122 Markdown.Append(MarkdownDocument.Encode(Reason));
123 Markdown.AppendLine(" |");
124
125 Markdown.Append("| Response desired: | ");
126 if (ResponseDesired)
127 Markdown.Append(":white_check_mark:");
128 else
129 Markdown.Append(":negative_squared_cross_mark:");
130 Markdown.AppendLine(" |");
131
133
134 Markdown.Append("| Date | ");
135 Markdown.Append(MarkdownDocument.Encode(Now.ToShortDateString()));
136 Markdown.AppendLine(" |");
137 Markdown.Append("| Time | ");
138 Markdown.Append(MarkdownDocument.Encode(Now.ToLongTimeString()));
139 Markdown.AppendLine(" |");
140
141 Markdown.AppendLine();
142 Markdown.AppendLine();
143 Markdown.AppendLine("```");
144 Markdown.AppendLine(Text.Replace("```", " ` ` ` "));
145 Markdown.AppendLine("```");
146
147 await LoginAuditor.AppendWhoIsInfo(Markdown, Request.RemoteEndPoint);
148
150 await IoTGateway.Gateway.SendNotification(Markdown.ToString());
151 else
152 Log.Notice(Markdown.ToString(), Tags);
153
154 await Response.SendResponse(new SeeOtherException("/FeedbackSent.md")); // PRG pattern.
155 }
156 else
157 await Response.SendResponse(new ForbiddenException(Request, "Request not verified. Bot?"));
158 }
159
166 public static async Task<bool> SiteVerify(string RecaptchaResponse, string RemoteEndPoint)
167 {
168 using HttpClient WebClient = new HttpClient();
169 Dictionary<string, string> VerificationForm = new Dictionary<string, string>()
170 {
171 { "secret", "6LcHNh0UAAAAAI1DwveBT21M4IkSRc5i-QciPUvg" }, // TODO: Make configurable.
172 { "response", RecaptchaResponse },
173 { "remoteip", RemoteEndPoint }
174 };
175
176 HttpContent Content = new FormUrlEncodedContent(VerificationForm);
177 HttpResponseMessage ResponseMsg = await WebClient.PostAsync("https://www.google.com/recaptcha/api/siteverify", Content);
178 if (!ResponseMsg.IsSuccessStatusCode)
179 throw new ServiceUnavailableException();
180
181 string Json = await ResponseMsg.Content.ReadAsStringAsync();
182
183 return JSON.Parse(Json) is Dictionary<string, object> Parsed &&
184 Parsed.ContainsKey("success") &&
185 Parsed["success"] is bool Success &&
186 Success;
187 }
188
189 }
190}
Helps with parsing of commong data types.
Definition: CommonTypes.cs:15
static bool TryParse(string s, out double Value)
Tries to decode a string encoded double.
Definition: CommonTypes.cs:48
Contains information about a response to a content request.
bool HasError
If an error occurred.
object Decoded
Decoded object.
Helps with common JSON-related tasks.
Definition: JSON.cs:16
static object Parse(string Json)
Parses a JSON string.
Definition: JSON.cs:45
Contains a markdown document. This markdown document class supports original markdown,...
static string Encode(string s)
Encodes all special characters in a string so that it can be included in a markdown document without ...
Static class managing the application event log. Applications and services log events on this static ...
Definition: Log.cs:14
static void Notice(string Message, string Object, string Actor, string EventId, EventLevel Level, string Facility, string Module, string StackTrace, params KeyValuePair< string, object >[] Tags)
Logs a notice event.
Definition: Log.cs:460
The request could not be understood by the server due to malformed syntax. The client SHOULD NOT repe...
The server understood the request, but is refusing to fulfill it. Authorization will not help and the...
Represents an HTTP request.
Definition: HttpRequest.cs:22
string RemoteEndPoint
Remote end-point.
Definition: HttpRequest.cs:243
bool HasData
If the request has data.
Definition: HttpRequest.cs:113
SessionVariables Session
Contains session states, if the resource requires sessions, or null otherwise.
Definition: HttpRequest.cs:212
async Task< ContentResponse > DecodeDataAsync()
Decodes data sent in request.
Definition: HttpRequest.cs:139
Represets a response of an HTTP client request.
Definition: HttpResponse.cs:23
async Task SendResponse()
Sends the response back to the client. If the resource is synchronous, there's no need to call this m...
Base class for all synchronous HTTP resources. A synchronous resource responds within the method hand...
The response to the request can be found under a different URI and SHOULD be retrieved using a GET me...
The server is currently unable to handle the request due to a temporary overloading or maintenance of...
Class that monitors login events, and help applications determine malicious intent....
Definition: LoginAuditor.cs:26
static async Task< string > AppendWhoIsInfo(StringBuilder Markdown, string RemoteEndPoint)
Appends WHOIS information to a Markdown document.
static async Task< KeyValuePair< string, object >[]> Annotate(string RemoteEndPoint, params KeyValuePair< string, object >[] Tags)
Annotates a remote endpoint.
Provides the user with options to control notifications from the Broker.
static BrokerNotificationConfiguration Instance
Current instance of configuration.
bool FeedbackReceived
If a notification should be sent when feedback has been received.
async Task POST(HttpRequest Request, HttpResponse Response)
Executes the POST method on the resource.
Definition: Feedback.cs:26
static async Task< bool > SiteVerify(string RecaptchaResponse, string RemoteEndPoint)
Allows web pages and web services to verify that Google reCaptcha responses are valid.
Definition: Feedback.cs:166
bool AllowsPOST
If the POST method is allowed.
Definition: Feedback.cs:24
Service Module hosting the XMPP broker and its components.
static async Task AppendRemoteEndPointToTable(StringBuilder Markdown, string RemoteEndPoint)
Appends annotated information about a remote endpoint to a Markdown table.
POST Interface for HTTP resources.