How to fetch API resource by ID when ID is not in Nuxt page params - vue.js

I have a RESTful (Django) API which (amongst others) serves a resource called CourseType. CourseType has an ID but it also has a slug.
In my frontend site (built with Nuxt), the URL I'd like to use is something like:-
http://example.com/courses/<course slug>/
ie. I don't want to use the course ID in the URL.
But the course slugs are not unique in the database. So I can't just fetch the course using its slug as a lookup - I need to look it up using its ID.
What is the best way of doing this from a Nuxt point of view?
I do have access to all of the courses in the Vuex store - as they have been retrieved in a previous API call - so I could find the course slug in the store of courses and then use the ID to do the API call for that course. But is that the best way or should I be doing something else?
I'm quite new to Nuxt so this is all pretty challenging for me!

Related

Get Magento 2 customer ID in Vue front-end

I am working on Vue Storefront ( a Nuxt.js with Express.js based framework) where GraphQL queries are used to get data from Magento 2.
I tried to add customers ID in the GraphQL query for customer data but it returned as Null (see response below). I've read this is not recommended but I still want to try something in my client with the Customer ID.
"data":{
"customer":{
"__typename":"Customer",
"date_of_birth":null,
"email":"john#doe.com",
"firstname":"john",
"is_subscribed":false,
"id":null,
"addresses":[
...
How can I, safety risks aside, still aquire the Customer ID in my front-end? Is there a small GraphQl query I can execute as a javascript function? I also have an Express.js part of my app where I can securely request and send data to other platforms (this is server side).

OpenAlex API - How to get institution ID?

I am trying to use the OpenAlex API: https://docs.openalex.org/api
This API provides access to a catalog of scholarly papers, authors, institutions, etc...
It is easy enough to make a query for an institution's information such. Here is an example from the API docs:
https://api.openalex.org/I19820366
I am trying to figure out how to get a specific institution's ID.
In the docs, there is a statement that this ID number is Microsoft Academic Graph's institutional ID: https://www.microsoft.com/en-us/research/project/microsoft-academic-graph/
But I have been unable to figure out anything in Microsoft Academic Graph either.
How can I find the institutional ID for a specific institution?
I am a beginner, and I also just started to retrieve data from the OpenAlex API. For me, the easiest way was either to use the ROR id or the GRID id, which you can both look up for any institution either here: https://www.grid.ac/ or here: https://ror.org/
Then you use either ROR or GRID-ID as an identifier (https://docs.openalex.org/about-the-data/institution#ids) and that identifier as a filter, as specified in the API documentation.
Be aware, that except for the Institution-ID, that you want to find, all the other institutional IDs, like ROR or GRID, have to be put in your request as a full URL. Take the example of the Johns Hopkins University. It's not enough to put their ROR like this: "00za53h95", you have to put in the API request like that: "https://ror.org/00za53h95" (without the quotes) or else it won't work. In my example, a request could look like this:
https://api.openalex.org/institutions/https://ror.org/00za53h95
This will deliver a nice json file with all the info you need, including the institution's ID in the database. Save the information as a file by using a cURL GET request or just do it via your browser and get the result as a webpage, both works. If you do the latter, you should follow the suggestion of the OpenAlex team and install a browser plugin like JSONVue, that will make the experience of reading the result on your screen so much better.
Hope that helps.
You can use the OpenAlex API to search for the ID like this:
https://api.openalex.org/institutions?filter=display_name.search:University%20of%20Virginia
In addition to Heather's comment, I'd like to add that we can now go to https://explore.openalex.org/ and search for any entity. Start typing "Johns Hopkins University" and you'll get to this page: https://explore.openalex.org/institutions/I145311948 which has all the identifiers (including the openalex id I145311948) and additional information about this institution.

API design pattern to be integrated both by own web app and other systems

So this backend will be consumed by an ad-hoc front end application. But will also be integrated by other systems and we will expose API for them.
When designing the rest I see that there is ONE database table (we call it for table A) that can join many other tables, lets say about 10 to 20 other tables.
Now, my strategy would be to build routes in my backend that will "reason" according to the ad-hoc frontend we have.
So if there is a page in the frontend (let's call this page for page1) that requires to get rows from the table A but also fields from let's say 3 other join tables, then I want to create a route in the backend called maybe "page1" which will return rows from table A and also from the other 3 tables.
This is of course an ordinary way to build a backend. But as it will also be used by other systems then somebody could argue that these systems maybe don't have any need for the route "page1". Their frontend will maybe never build a "page1".
So according to people here, it would better to build the API more agnostically. And instead of creating the route "page1" I should build it according to "hateoas". And if I understand that principle, instead of letting my ad-hoc frontend to request the resource "page1" it would request "pageForTableA". And then, the resource "pageForTableA" should return which are the possible table to be joined.
In this case, for my frontend's page1, I would need to make 4 subsequent request to the server, instead of one like I would like to do if there was a "page1" resource in the backend.
What do you think?
I also see a thirt strategy. I don't know if there is a name for this pattern but it would be this way:
A resource in backend that returns only rows from table A. BUT, the route also takes arguments. And the argument is an array with the name of all the other tables someone want to include.
So if frontend calls:
getTableA(array('tableB', 'tableD', 'tableF'))
Then the resource would include/join the tables B, D and F. In short: API resource let's the frontend decide what it want to get delivered.
Which of these 3 strategies are best do you think? Or there is some more that could be taken in consideration?
You need to architect your API in a way that consumers shouldn't know about how the data is stored in the underlying data store.
Furthermore, if you want to allow consumers to decide which fields you want to project in the response, you could give them using some query string format.
BTW, maybe you should avoid re-inventing the wheel. There's a standard called Open Data (OData) which already defines a lot of things like you already require in your API, and since it has been made by Microsoft, it has deep support on .NET.
Check this tutorial (Create an OData v4 Endpoint Using ASP.NET Web API 2.2) to get more in touch with OData.

Flask REST api resource URLs suggestions

I'm working on REST Api suing Python Flask, as I have more and more routes, its hard to manage all the resource urls.
Right now, I'm confused which one is better practices of URL parameters. Examples below:
Get a list of courses with limits:
/courses/<int:lim> OR /courses/list?lim=10
Get a specific course:
/courses/<code>/<section> OR /courses/show?code=cs100&section=1
Get a list of students in specific course:
/courses/<code>/<section>/students OR /students/show?code=cs100&section=1
Should I pass query parameters using / or by doing ?
The only reason I'm using / is that there's no conflict in query.
If I have these two URL for two different queries, how can I fix it so I can query base on the parameters:
/students/show?code=cs100&section=1 (Get all students in that course)
/students/show?id=123456789 (Get the specific student)
The URL should identify a resource or collection of resources. Any options you want to give the client, such as pagination, limits, filtering, sorting, etc. I think is best to include in the query string or in HTTP headers.
So regarding your specific questions:
Get a list of courses with limits: /courses/<int:lim> OR /courses/list?lim=10
Neither one. Use /courses?lim=10. No need to have a /list component, that is an action, not a resource.
Get a specific course: /courses/<code>/<section> OR /courses/show?code=cs100&section=1
The first. Once again, /courses/show indicates an action, you want URLs to be links to resources, in this case your course.
Get a list of students in specific course: /courses/<code>/<section>/students OR /students/show?code=cs100&section=1
The first, same reason as the previous one.
I have given REST API talks at the last two PyCon conferences, feel free to check them out if you want to learn more API design best practices:
PyCon 2014: Writing RESTful Web Services with Flask
PyCon 2015: Is Your REST API RESTful?

REST api / url design for resources with pluralization / post methods

Say, for example, I had a REST api url design with "Customer" as a resource.
Now, I want to be able to list all customers, find a specific customer by ID or Email address
Also, I want to be able to add a new customer...
Are these example URIs right?
Or should I be doing it another way..?
/customer/1234
get customer with id 1234
/customer/email/john#smith.com
get customer with email address
[POST]
/customer/
creates a new customer
/customers/
list all customers (notice pluralization)
In my experience RESTful APIs use a single resource path that is plural. The idea is that you have customers and when you want to interact with a customer you are interacting with the customers resource in general.
GET /customers to get a list of customers.
POST /customers to create a new customer.
GET /customers/:id to get a specific customer with a unique id. (Generally not an attribute of a customer like email)
GET /customers?email=bob#example.com to get customers with a specific attribute value.
Apigee has a blog post that covers pluralization that you might want to read.
If I was designing this API I would start with a generic hypermedia type like HAL and design a root representation that provides me access to the various scenarios you describe using links and uri templates.
e.g
GET /api
=>
<resource>
<link rel="urn:mycompany:customer" href=".../{id}"/>
<link rel="urn:mycompany:customers" href="..."/>
<link rel="urn:mycompany:customersearch" href="...{?email}"/>
</resource>
I have not filled in the actual URLs because from the perspective of the consumer of the API it really does not matter how those URLs are structured. Do whatever is easiest in you server framework. Don't worry if you get it wrong, you can change it later and your clients won't break because they should discover the URL from the root representation.
It is fairly common to assume that POSTing a customer to a collection of customers will create a new Customer, so you could just require your consumers to use that link. Or if you wish to be more explicit you could define a new link relation that provides a URL for creating Customers.
This is how I would do it:
/customer/1234
customer/john#smith.com
or (if email not guaranteed to be unique)
customers/search?email=john#smith.com
[POST]
/customers/ (notice the plural, same as below)
[GET]
/customers/
Cheers,
Ferenc
Why not be robust and enable both /customer and /customers?
GET /customer/1234 or /customers/1234 retrieves the same resource.
GET on /customer or /customers gives a list of all customers.
POST to /customer or /customers creates a new customer.