C# OData GetKeyFromUri - Resource not found for the segment 'odata'
I've updated from Microsoft.AspNet.OData version 6.0.0 to OData version 7.0.1. The upgrade has broken my ability to get the Id from a path when linking one object to another. Here is my Web API call to add a role to a specific user using the OData standard:
POST: http://localhost:61506/odata/users('bob')/roles/$ref
Request body: {"@odata.id":"http://localhost:61506/odata/roles(1)"}
The Web API method verifies the user and then makes a call to Helpers.GetKeyFromUri to get the role Id value from the request body.
[HttpPost, HttpPut]
public IHttpActionResult CreateRef([FromODataUri] string key, string navigationProperty, [FromBody] Uri link)
{
// Ensure the User exists
User user = new User().GetById(key);
if (user == null)
{
return NotFound();
}
// Determine which navigation property to use
switch (navigationProperty)
{
case "roles":
// Get the Role id
int roleId;
try
{
roleId = Helpers.GetKeyFromUri<int>(Request, link);
}
catch (Exception ex)
{
return BadRequest();
}
// Ensure the Role exists
Role role = new Role().GetById(roleId);
if (role == null)
{
return NotFound();
}
// Add the User/Role relationship
user.Roles.Add(role);
user.Update();
break;
default:
return StatusCode(HttpStatusCode.NotImplemented);
}
return StatusCode(HttpStatusCode.NoContent);
}
That function looks like this (Originally from here but with updated references: https://github.com/OData/ODataSamples/blob/master/RESTier/Trippin/Trippin/Helpers.cs)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Web.Http.Routing;
using Microsoft.AspNet.OData.Extensions;
using Microsoft.AspNet.OData.Routing;
using Microsoft.OData.UriParser;
namespace Project1.Extensions
{
public class Helpers
{
public static TKey GetKeyFromUri<TKey>(HttpRequestMessage request, Uri uri)
{
if (uri == null)
{
throw new ArgumentNullException("uri");
}
var urlHelper = request.GetUrlHelper() ?? new UrlHelper(request);
var pathHandler = (IODataPathHandler)request.GetRequestContainer().GetService(typeof(IODataPathHandler));
string serviceRoot = urlHelper.CreateODataLink(
request.ODataProperties().RouteName,
pathHandler, new List<ODataPathSegment>());
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
var keySegment = odataPath.Segments.OfType<KeySegment>().FirstOrDefault();
if (keySegment == null)
{
throw new InvalidOperationException("The link does not contain a key.");
}
var value = keySegment.Keys.FirstOrDefault().Value;
return (TKey)value;
}
}
}
This line of code is now throwing the following error: Resource not found for the segment 'odata'
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
This worked fine when using OData 6.0.0 but fails in 7.0.1. It seems to have some sort of issue parsing my odata segment or not being able to find it at all. Here is my routing setup if it helps:
public static void Register(HttpConfiguration config)
{
// Setup the OData routes and endpoints
config.MapODataServiceRoute(
routeName: "ODataRoute",
routePrefix: "odata",
model: GetEdmModel());
// Enable OData URL querying globally
config.Count().Filter().Select().OrderBy().Expand().MaxTop(null);
}
odata
add a comment |
I've updated from Microsoft.AspNet.OData version 6.0.0 to OData version 7.0.1. The upgrade has broken my ability to get the Id from a path when linking one object to another. Here is my Web API call to add a role to a specific user using the OData standard:
POST: http://localhost:61506/odata/users('bob')/roles/$ref
Request body: {"@odata.id":"http://localhost:61506/odata/roles(1)"}
The Web API method verifies the user and then makes a call to Helpers.GetKeyFromUri to get the role Id value from the request body.
[HttpPost, HttpPut]
public IHttpActionResult CreateRef([FromODataUri] string key, string navigationProperty, [FromBody] Uri link)
{
// Ensure the User exists
User user = new User().GetById(key);
if (user == null)
{
return NotFound();
}
// Determine which navigation property to use
switch (navigationProperty)
{
case "roles":
// Get the Role id
int roleId;
try
{
roleId = Helpers.GetKeyFromUri<int>(Request, link);
}
catch (Exception ex)
{
return BadRequest();
}
// Ensure the Role exists
Role role = new Role().GetById(roleId);
if (role == null)
{
return NotFound();
}
// Add the User/Role relationship
user.Roles.Add(role);
user.Update();
break;
default:
return StatusCode(HttpStatusCode.NotImplemented);
}
return StatusCode(HttpStatusCode.NoContent);
}
That function looks like this (Originally from here but with updated references: https://github.com/OData/ODataSamples/blob/master/RESTier/Trippin/Trippin/Helpers.cs)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Web.Http.Routing;
using Microsoft.AspNet.OData.Extensions;
using Microsoft.AspNet.OData.Routing;
using Microsoft.OData.UriParser;
namespace Project1.Extensions
{
public class Helpers
{
public static TKey GetKeyFromUri<TKey>(HttpRequestMessage request, Uri uri)
{
if (uri == null)
{
throw new ArgumentNullException("uri");
}
var urlHelper = request.GetUrlHelper() ?? new UrlHelper(request);
var pathHandler = (IODataPathHandler)request.GetRequestContainer().GetService(typeof(IODataPathHandler));
string serviceRoot = urlHelper.CreateODataLink(
request.ODataProperties().RouteName,
pathHandler, new List<ODataPathSegment>());
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
var keySegment = odataPath.Segments.OfType<KeySegment>().FirstOrDefault();
if (keySegment == null)
{
throw new InvalidOperationException("The link does not contain a key.");
}
var value = keySegment.Keys.FirstOrDefault().Value;
return (TKey)value;
}
}
}
This line of code is now throwing the following error: Resource not found for the segment 'odata'
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
This worked fine when using OData 6.0.0 but fails in 7.0.1. It seems to have some sort of issue parsing my odata segment or not being able to find it at all. Here is my routing setup if it helps:
public static void Register(HttpConfiguration config)
{
// Setup the OData routes and endpoints
config.MapODataServiceRoute(
routeName: "ODataRoute",
routePrefix: "odata",
model: GetEdmModel());
// Enable OData URL querying globally
config.Count().Filter().Select().OrderBy().Expand().MaxTop(null);
}
odata
add a comment |
I've updated from Microsoft.AspNet.OData version 6.0.0 to OData version 7.0.1. The upgrade has broken my ability to get the Id from a path when linking one object to another. Here is my Web API call to add a role to a specific user using the OData standard:
POST: http://localhost:61506/odata/users('bob')/roles/$ref
Request body: {"@odata.id":"http://localhost:61506/odata/roles(1)"}
The Web API method verifies the user and then makes a call to Helpers.GetKeyFromUri to get the role Id value from the request body.
[HttpPost, HttpPut]
public IHttpActionResult CreateRef([FromODataUri] string key, string navigationProperty, [FromBody] Uri link)
{
// Ensure the User exists
User user = new User().GetById(key);
if (user == null)
{
return NotFound();
}
// Determine which navigation property to use
switch (navigationProperty)
{
case "roles":
// Get the Role id
int roleId;
try
{
roleId = Helpers.GetKeyFromUri<int>(Request, link);
}
catch (Exception ex)
{
return BadRequest();
}
// Ensure the Role exists
Role role = new Role().GetById(roleId);
if (role == null)
{
return NotFound();
}
// Add the User/Role relationship
user.Roles.Add(role);
user.Update();
break;
default:
return StatusCode(HttpStatusCode.NotImplemented);
}
return StatusCode(HttpStatusCode.NoContent);
}
That function looks like this (Originally from here but with updated references: https://github.com/OData/ODataSamples/blob/master/RESTier/Trippin/Trippin/Helpers.cs)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Web.Http.Routing;
using Microsoft.AspNet.OData.Extensions;
using Microsoft.AspNet.OData.Routing;
using Microsoft.OData.UriParser;
namespace Project1.Extensions
{
public class Helpers
{
public static TKey GetKeyFromUri<TKey>(HttpRequestMessage request, Uri uri)
{
if (uri == null)
{
throw new ArgumentNullException("uri");
}
var urlHelper = request.GetUrlHelper() ?? new UrlHelper(request);
var pathHandler = (IODataPathHandler)request.GetRequestContainer().GetService(typeof(IODataPathHandler));
string serviceRoot = urlHelper.CreateODataLink(
request.ODataProperties().RouteName,
pathHandler, new List<ODataPathSegment>());
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
var keySegment = odataPath.Segments.OfType<KeySegment>().FirstOrDefault();
if (keySegment == null)
{
throw new InvalidOperationException("The link does not contain a key.");
}
var value = keySegment.Keys.FirstOrDefault().Value;
return (TKey)value;
}
}
}
This line of code is now throwing the following error: Resource not found for the segment 'odata'
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
This worked fine when using OData 6.0.0 but fails in 7.0.1. It seems to have some sort of issue parsing my odata segment or not being able to find it at all. Here is my routing setup if it helps:
public static void Register(HttpConfiguration config)
{
// Setup the OData routes and endpoints
config.MapODataServiceRoute(
routeName: "ODataRoute",
routePrefix: "odata",
model: GetEdmModel());
// Enable OData URL querying globally
config.Count().Filter().Select().OrderBy().Expand().MaxTop(null);
}
odata
I've updated from Microsoft.AspNet.OData version 6.0.0 to OData version 7.0.1. The upgrade has broken my ability to get the Id from a path when linking one object to another. Here is my Web API call to add a role to a specific user using the OData standard:
POST: http://localhost:61506/odata/users('bob')/roles/$ref
Request body: {"@odata.id":"http://localhost:61506/odata/roles(1)"}
The Web API method verifies the user and then makes a call to Helpers.GetKeyFromUri to get the role Id value from the request body.
[HttpPost, HttpPut]
public IHttpActionResult CreateRef([FromODataUri] string key, string navigationProperty, [FromBody] Uri link)
{
// Ensure the User exists
User user = new User().GetById(key);
if (user == null)
{
return NotFound();
}
// Determine which navigation property to use
switch (navigationProperty)
{
case "roles":
// Get the Role id
int roleId;
try
{
roleId = Helpers.GetKeyFromUri<int>(Request, link);
}
catch (Exception ex)
{
return BadRequest();
}
// Ensure the Role exists
Role role = new Role().GetById(roleId);
if (role == null)
{
return NotFound();
}
// Add the User/Role relationship
user.Roles.Add(role);
user.Update();
break;
default:
return StatusCode(HttpStatusCode.NotImplemented);
}
return StatusCode(HttpStatusCode.NoContent);
}
That function looks like this (Originally from here but with updated references: https://github.com/OData/ODataSamples/blob/master/RESTier/Trippin/Trippin/Helpers.cs)
using System;
using System.Collections.Generic;
using System.Linq;
using System.Net.Http;
using System.Web.Http.Routing;
using Microsoft.AspNet.OData.Extensions;
using Microsoft.AspNet.OData.Routing;
using Microsoft.OData.UriParser;
namespace Project1.Extensions
{
public class Helpers
{
public static TKey GetKeyFromUri<TKey>(HttpRequestMessage request, Uri uri)
{
if (uri == null)
{
throw new ArgumentNullException("uri");
}
var urlHelper = request.GetUrlHelper() ?? new UrlHelper(request);
var pathHandler = (IODataPathHandler)request.GetRequestContainer().GetService(typeof(IODataPathHandler));
string serviceRoot = urlHelper.CreateODataLink(
request.ODataProperties().RouteName,
pathHandler, new List<ODataPathSegment>());
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
var keySegment = odataPath.Segments.OfType<KeySegment>().FirstOrDefault();
if (keySegment == null)
{
throw new InvalidOperationException("The link does not contain a key.");
}
var value = keySegment.Keys.FirstOrDefault().Value;
return (TKey)value;
}
}
}
This line of code is now throwing the following error: Resource not found for the segment 'odata'
var odataPath = pathHandler.Parse(serviceRoot, uri.LocalPath, request.GetRequestContainer());
This worked fine when using OData 6.0.0 but fails in 7.0.1. It seems to have some sort of issue parsing my odata segment or not being able to find it at all. Here is my routing setup if it helps:
public static void Register(HttpConfiguration config)
{
// Setup the OData routes and endpoints
config.MapODataServiceRoute(
routeName: "ODataRoute",
routePrefix: "odata",
model: GetEdmModel());
// Enable OData URL querying globally
config.Count().Filter().Select().OrderBy().Expand().MaxTop(null);
}
odata
odata
asked Nov 10 at 18:03
user1624184
427
427
add a comment |
add a comment |
1 Answer
1
active
oldest
votes
I caused myself the same problem by changing routePrefix
from null
to odata
just like you've done. Setting routePrefix
to null
will allow your code to work perfectly fine as long as you don't need a route prefix (such as /odata/
).
New contributor
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
add a comment |
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%2f53241904%2fc-sharp-odata-getkeyfromuri-resource-not-found-for-the-segment-odata%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
I caused myself the same problem by changing routePrefix
from null
to odata
just like you've done. Setting routePrefix
to null
will allow your code to work perfectly fine as long as you don't need a route prefix (such as /odata/
).
New contributor
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
add a comment |
I caused myself the same problem by changing routePrefix
from null
to odata
just like you've done. Setting routePrefix
to null
will allow your code to work perfectly fine as long as you don't need a route prefix (such as /odata/
).
New contributor
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
add a comment |
I caused myself the same problem by changing routePrefix
from null
to odata
just like you've done. Setting routePrefix
to null
will allow your code to work perfectly fine as long as you don't need a route prefix (such as /odata/
).
New contributor
I caused myself the same problem by changing routePrefix
from null
to odata
just like you've done. Setting routePrefix
to null
will allow your code to work perfectly fine as long as you don't need a route prefix (such as /odata/
).
New contributor
edited 5 hours ago
Joe McMahon
2,3021226
2,3021226
New contributor
answered 14 hours ago
Jonathan Pickard
1
1
New contributor
New contributor
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
add a comment |
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not really answer the question. If you have a different question, you can ask it by clicking Ask Question. You can also add a bounty to draw more attention to this question once you have enough reputation. - From Review
– Simonare
14 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
This does not provide an answer to the question. Once you have sufficient reputation you will be able to comment on any post; instead, provide answers that don't require clarification from the asker. - From Review
– Ian Lim
6 hours ago
add a comment |
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.
Some of your past answers have not been well-received, and you're in danger of being blocked from answering.
Please pay close attention to the following guidance:
- 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%2f53241904%2fc-sharp-odata-getkeyfromuri-resource-not-found-for-the-segment-odata%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