Response body unchanged after being processed by middleware
I am trying to write a middleware that calls the next middleware and then whatever the response body of that middleware is, it will be changed by my middleware.
This is what the Configuration()
method in the Startup
class looks like:
public void Configuration(IAppBuilder app)
{
app.Use<OAuthAuthenticationFailCustomResponse>();
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
This is the middleware written by me:
public class OAuthAuthenticationFailCustomResponse : OwinMiddleware
{
public OAuthAuthenticationFailCustomResponse(OwinMiddleware next)
: base(next)
{
}
public async override Task Invoke(IOwinContext context)
{
var stream = context.Response.Body;
using (var buffer = new MemoryStream())
{
context.Response.Body = buffer;
await Next.Invoke(context);
buffer.Seek(0, SeekOrigin.Begin);
var byteArray = Encoding.ASCII.GetBytes("Hello World");
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
buffer.SetLength(0);
buffer.Write(byteArray, 0, byteArray.Length);
buffer.Seek(0, SeekOrigin.Begin);
buffer.CopyTo(stream);
}
}
}
However, I still receive the response of the OAuthBearerAuthentication
middleware after calling the API, which is:
{
"Message": "Authorization has been denied for this request." }
This is where I learnt to write the code that changes the response body;
c# asp.net-web-api2 owin-middleware
add a comment |
I am trying to write a middleware that calls the next middleware and then whatever the response body of that middleware is, it will be changed by my middleware.
This is what the Configuration()
method in the Startup
class looks like:
public void Configuration(IAppBuilder app)
{
app.Use<OAuthAuthenticationFailCustomResponse>();
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
This is the middleware written by me:
public class OAuthAuthenticationFailCustomResponse : OwinMiddleware
{
public OAuthAuthenticationFailCustomResponse(OwinMiddleware next)
: base(next)
{
}
public async override Task Invoke(IOwinContext context)
{
var stream = context.Response.Body;
using (var buffer = new MemoryStream())
{
context.Response.Body = buffer;
await Next.Invoke(context);
buffer.Seek(0, SeekOrigin.Begin);
var byteArray = Encoding.ASCII.GetBytes("Hello World");
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
buffer.SetLength(0);
buffer.Write(byteArray, 0, byteArray.Length);
buffer.Seek(0, SeekOrigin.Begin);
buffer.CopyTo(stream);
}
}
}
However, I still receive the response of the OAuthBearerAuthentication
middleware after calling the API, which is:
{
"Message": "Authorization has been denied for this request." }
This is where I learnt to write the code that changes the response body;
c# asp.net-web-api2 owin-middleware
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47
add a comment |
I am trying to write a middleware that calls the next middleware and then whatever the response body of that middleware is, it will be changed by my middleware.
This is what the Configuration()
method in the Startup
class looks like:
public void Configuration(IAppBuilder app)
{
app.Use<OAuthAuthenticationFailCustomResponse>();
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
This is the middleware written by me:
public class OAuthAuthenticationFailCustomResponse : OwinMiddleware
{
public OAuthAuthenticationFailCustomResponse(OwinMiddleware next)
: base(next)
{
}
public async override Task Invoke(IOwinContext context)
{
var stream = context.Response.Body;
using (var buffer = new MemoryStream())
{
context.Response.Body = buffer;
await Next.Invoke(context);
buffer.Seek(0, SeekOrigin.Begin);
var byteArray = Encoding.ASCII.GetBytes("Hello World");
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
buffer.SetLength(0);
buffer.Write(byteArray, 0, byteArray.Length);
buffer.Seek(0, SeekOrigin.Begin);
buffer.CopyTo(stream);
}
}
}
However, I still receive the response of the OAuthBearerAuthentication
middleware after calling the API, which is:
{
"Message": "Authorization has been denied for this request." }
This is where I learnt to write the code that changes the response body;
c# asp.net-web-api2 owin-middleware
I am trying to write a middleware that calls the next middleware and then whatever the response body of that middleware is, it will be changed by my middleware.
This is what the Configuration()
method in the Startup
class looks like:
public void Configuration(IAppBuilder app)
{
app.Use<OAuthAuthenticationFailCustomResponse>();
app.UseOAuthBearerAuthentication(new OAuthBearerAuthenticationOptions());
}
This is the middleware written by me:
public class OAuthAuthenticationFailCustomResponse : OwinMiddleware
{
public OAuthAuthenticationFailCustomResponse(OwinMiddleware next)
: base(next)
{
}
public async override Task Invoke(IOwinContext context)
{
var stream = context.Response.Body;
using (var buffer = new MemoryStream())
{
context.Response.Body = buffer;
await Next.Invoke(context);
buffer.Seek(0, SeekOrigin.Begin);
var byteArray = Encoding.ASCII.GetBytes("Hello World");
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
buffer.SetLength(0);
buffer.Write(byteArray, 0, byteArray.Length);
buffer.Seek(0, SeekOrigin.Begin);
buffer.CopyTo(stream);
}
}
}
However, I still receive the response of the OAuthBearerAuthentication
middleware after calling the API, which is:
{
"Message": "Authorization has been denied for this request." }
This is where I learnt to write the code that changes the response body;
c# asp.net-web-api2 owin-middleware
c# asp.net-web-api2 owin-middleware
edited Jan 1 at 11:04
Nkosi
116k16130194
116k16130194
asked Jan 1 at 10:39
Khanh CTGKhanh CTG
317516
317516
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47
add a comment |
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47
add a comment |
1 Answer
1
active
oldest
votes
The original stream was not put back into the context response body
public async override Task Invoke(IOwinContext context) {
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream()) {
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await Next.Invoke(context);
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream from the buffer
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
//...decide what you want to do with the responseBody from other middleware
//custom response
var byteArray = Encoding.ASCII.GetBytes("Hello World");
//write custom response to stream
stream.Write(byteArray, 0, byteArray.Length);
//reset the response body back to the original stream
context.Response.Body = stream;
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
}
}
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
|
show 2 more comments
Your Answer
StackExchange.ifUsing("editor", function () {
StackExchange.using("externalEditor", function () {
StackExchange.using("snippets", function () {
StackExchange.snippets.init();
});
});
}, "code-snippets");
StackExchange.ready(function() {
var channelOptions = {
tags: "".split(" "),
id: "1"
};
initTagRenderer("".split(" "), "".split(" "), channelOptions);
StackExchange.using("externalEditor", function() {
// Have to fire editor after snippets, if snippets enabled
if (StackExchange.settings.snippets.snippetsEnabled) {
StackExchange.using("snippets", function() {
createEditor();
});
}
else {
createEditor();
}
});
function createEditor() {
StackExchange.prepareEditor({
heartbeatType: 'answer',
autoActivateHeartbeat: false,
convertImagesToLinks: true,
noModals: true,
showLowRepImageUploadWarning: true,
reputationToPostImages: 10,
bindNavPrevention: true,
postfix: "",
imageUploader: {
brandingHtml: "Powered by u003ca class="icon-imgur-white" href="https://imgur.com/"u003eu003c/au003e",
contentPolicyHtml: "User contributions licensed under u003ca href="https://creativecommons.org/licenses/by-sa/3.0/"u003ecc by-sa 3.0 with attribution requiredu003c/au003e u003ca href="https://stackoverflow.com/legal/content-policy"u003e(content policy)u003c/au003e",
allowUrls: true
},
onDemand: true,
discardSelector: ".discard-answer"
,immediatelyShowMarkdownHelp:true
});
}
});
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53994795%2fresponse-body-unchanged-after-being-processed-by-middleware%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
1 Answer
1
active
oldest
votes
1 Answer
1
active
oldest
votes
active
oldest
votes
active
oldest
votes
The original stream was not put back into the context response body
public async override Task Invoke(IOwinContext context) {
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream()) {
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await Next.Invoke(context);
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream from the buffer
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
//...decide what you want to do with the responseBody from other middleware
//custom response
var byteArray = Encoding.ASCII.GetBytes("Hello World");
//write custom response to stream
stream.Write(byteArray, 0, byteArray.Length);
//reset the response body back to the original stream
context.Response.Body = stream;
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
}
}
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
|
show 2 more comments
The original stream was not put back into the context response body
public async override Task Invoke(IOwinContext context) {
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream()) {
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await Next.Invoke(context);
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream from the buffer
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
//...decide what you want to do with the responseBody from other middleware
//custom response
var byteArray = Encoding.ASCII.GetBytes("Hello World");
//write custom response to stream
stream.Write(byteArray, 0, byteArray.Length);
//reset the response body back to the original stream
context.Response.Body = stream;
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
}
}
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
|
show 2 more comments
The original stream was not put back into the context response body
public async override Task Invoke(IOwinContext context) {
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream()) {
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await Next.Invoke(context);
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream from the buffer
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
//...decide what you want to do with the responseBody from other middleware
//custom response
var byteArray = Encoding.ASCII.GetBytes("Hello World");
//write custom response to stream
stream.Write(byteArray, 0, byteArray.Length);
//reset the response body back to the original stream
context.Response.Body = stream;
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
}
}
The original stream was not put back into the context response body
public async override Task Invoke(IOwinContext context) {
// hold a reference to what will be the outbound/processed response stream object
var stream = context.Response.Body;
// create a stream that will be sent to the response stream before processing
using (var buffer = new MemoryStream()) {
// set the response stream to the buffer to hold the unaltered response
context.Response.Body = buffer;
// allow other middleware to respond
await Next.Invoke(context);
// we have the unaltered response, go to start
buffer.Seek(0, SeekOrigin.Begin);
// read the stream from the buffer
var reader = new StreamReader(buffer);
string responseBody = reader.ReadToEnd();
//...decide what you want to do with the responseBody from other middleware
//custom response
var byteArray = Encoding.ASCII.GetBytes("Hello World");
//write custom response to stream
stream.Write(byteArray, 0, byteArray.Length);
//reset the response body back to the original stream
context.Response.Body = stream;
context.Response.StatusCode = 200;
context.Response.ContentLength = byteArray.Length;
}
}
edited Jan 1 at 11:17
answered Jan 1 at 10:49
NkosiNkosi
116k16130194
116k16130194
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
|
show 2 more comments
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
This is what I got: {"Message":"Authorization has been denied for this request."}Hello World. It seems like the string is just appended to the original response body.
– Khanh CTG
Jan 1 at 10:55
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
Are you trying to replace the response body or alter it?
– Nkosi
Jan 1 at 10:56
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
I am trying to replace the response body. The expected response body is "Hello World".
– Khanh CTG
Jan 1 at 10:57
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
@KhanhCTG Check update
– Nkosi
Jan 1 at 10:58
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
The following line threw System.NotSupportedException with message "Specified method is not supported.": stream.Seek(0, SeekOrigin.Begin);
– Khanh CTG
Jan 1 at 11:07
|
show 2 more comments
Thanks for contributing an answer to Stack Overflow!
- Please be sure to answer the question. Provide details and share your research!
But avoid …
- Asking for help, clarification, or responding to other answers.
- Making statements based on opinion; back them up with references or personal experience.
To learn more, see our tips on writing great answers.
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
StackExchange.ready(
function () {
StackExchange.openid.initPostLogin('.new-post-login', 'https%3a%2f%2fstackoverflow.com%2fquestions%2f53994795%2fresponse-body-unchanged-after-being-processed-by-middleware%23new-answer', 'question_page');
}
);
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Sign up or log in
StackExchange.ready(function () {
StackExchange.helpers.onClickDraftSave('#login-link');
});
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Sign up using Google
Sign up using Facebook
Sign up using Email and Password
Post as a guest
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
Required, but never shown
You did not put the original stream back into the context response body
– Nkosi
Jan 1 at 10:47