Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Issue in retrieving taxonomies #19

Open
dma82 opened this issue Jan 13, 2022 · 10 comments
Open

Issue in retrieving taxonomies #19

dma82 opened this issue Jan 13, 2022 · 10 comments

Comments

@dma82
Copy link

dma82 commented Jan 13, 2022

Hi there,

I tried to use this module to retrieve a specific term store but I got an OAuth issue when I tried to hit the following endpoint (which works fine from the browser):

https://<TENANT_ID>.sharepoint.com/_api/v2.1/termStore/groups/<GROUP_ID>/sets/<SET_ID>/terms

So I successfully used pnp_auth and @pnp/sp-taxonomy modules, but I was wondering if I can achieve the same result with sp-request library as it's quite handy the way for the authentication with credentials, and doesn't require other libraries), especially because I had to use an older version of the above modules, which are giving me several warnings (e.g. Accessing non-existent property 'ControlMode' of module exports inside circular dependency ).

If this functionality is already there, would you be able to provide me with an example of how to properly access a term store please? If not, would it be possible to introduce it in the next release?

Thank you very much.

Regards

@s-KaiNet
Copy link
Owner

Hi,

could you tell me what exact issue do you have? What is the error code or maybe a stack trace?

@dma82
Copy link
Author

dma82 commented Jan 13, 2022

Hi @s-KaiNet ,

Unfortunately the only response I'm getting says "OAuth only flow is enabled and the call has not been issued from an app".

I thought there was an issue with the App permissions set for the Term Store but then I was able to successfully get a response from Postman: that's why I switched to @pnp/sp-taxonomy and pnp-auth libraries, which are working fine but the former library is throwing a lot of these warnings:

_(node:2804) Warning: Accessing non-existent property 'ControlMode' of module exports inside circular dependency
(Use 'node --trace-warnings ...' to show where the warning was created)
(node:2804) Warning: Accessing non-existent property 'FieldTypes' of module exports inside circular dependency
etc...

That's why I was hoping to achieve the same result with sp-request and move away from the other libraries.

Anyway, this an extract of my code using the @pnp/sp-taxonomy and pnp-auth (which is working):
`

    const bootstrap = require("pnp-auth").bootstrap,
     
    taxonomy = require("@pnp/sp-taxonomy").taxonomy;

    async function getList () {
              let url = settings.sharepoint.url;
    
              bootstrap(taxonomy, {
                      username: settings.sharepoint.auth.username, 
                      password: settings.sharepoint.auth.password }, 
                      url);

             const set = _.map(await taxonomy.termStores.getByName("<TAXONOMY_NAME>").getTermSetById("<TERMSET_ID>").terms.get(), 
                list => _.pick(list, ['Id', 'Name', 'PathOfTerm']));
   
             console.log(set); 
      }

`

Thanks again for your help.

@s-KaiNet
Copy link
Owner

If pnp-auth works, then sp-request also should work. You could try inspecting HTTP requests to see the difference in the headers and authentication. Also, which kind of authentication do you use for sp-request? Is it the same as for pnp-auth?

@dma82
Copy link
Author

dma82 commented Jan 13, 2022

Yes, the authentication works fine, because I was able to upload files in SP as well as update several fields; the problem seems when I try accessing taxonomies:

I tried this with sp-request which gave me the "OAuth" issue:

let url = "https://<TENANT_ID>.sharepoint.com/_api/v2.1/termStore/groups/<GROUP_ID>/sets/<SET_ID>/terms"
const _sprequest = (req.sprequest = sprequest.create(settings.sharepoint.auth));

_sprequest.requestDigest(settings.sharepoint.url) 
        .then((digest) => {
            return _sprequest.get(url, {
                headers: {
                    "Accept": "application/json;odata=verbose",
                    "Content-Type": "application/json;odata=verbose",
                    "X-RequestDigest": digest,
                }
            })
        }).then((response) => {
              //  some code here
        }).catch((err) => {
            //  some code here
        });

Here the URL is different: in my previous example, the URL was simply https://<TENANT_ID>.sharepoint.com , instead this time I tried to directly access the term store (I wasn't sure what else I could do, since it seems SharePoint doesn't have specific methods like 'GetByTitle' for lists when it comes to Taxonomies...)

The documentation I found suggested to use the Client ID and Secret ID, or the Bearer token, but I need to keep using username and password...

Thank you @s-KaiNet :)

@s-KaiNet
Copy link
Owner

Does it work when you use a Client ID and Secret ID? Also maybe it doesn't work because legacy auth is disabled for you? You can try executing Get-SPOTenant and inspect LegacyAuthProtocolsEnabled property.

@dma82
Copy link
Author

dma82 commented Jan 13, 2022

I haven't tried the Client ID and Secret ID, but I've just generated the Bearer token from Postman and I passed it in this way and it worked:

let url = "https://<TENANT_ID>.sharepoint.com/_api/v2.1/termStore/groups/<GROUP_ID>/sets/<SET_ID>/terms"
const _sprequest = (req.sprequest = sprequest.create(settings.sharepoint.auth));

_sprequest({
            url,
            method: "GET",
            headers: {
                Accept: "application/json;odata=verbose",
                "Content-Type": "application/json;odata=verbose",
                "Authorization": "Bearer  <TOKEN GENERATED BY POSTMAN>"
            },
        }).then((response) => {
            res.locals.result = response.body;
            debug(res.locals.result)
            return next();
        }).catch((err) => {
            // Some code here
        });

Is there a different authentication protocol that it's working for the Bearer authorization? OAuth 2 maybe? Or am I missing something else?

@s-KaiNet
Copy link
Owner

When you use bearer tokens, then it's OAuth, with username\password it's cookie based auth, and it looks like it doesn't work with new taxonomy REST endpoint (_api/v2.1/termStore). Actually, it's just a 1:1 mapping between corresponding MS Graph API, MS Graph, in turn, doesn't support cookie auth and that explains why it doesn't work for you with username and password.

@dma82
Copy link
Author

dma82 commented Jan 13, 2022

So I guess there's no workaround for this, is there? :(

@s-KaiNet
Copy link
Owner

No, except using OAuth type of authentication. Alternatively, if you need a username and passwords and cannot get rid of it, you can implement ROPC flow with a regular Azure AD auth using msal. Once you have a bearer token, you can use a regular fetch API to send requests.

@dma82
Copy link
Author

dma82 commented Jan 13, 2022

I'll try that so and see what I get... I guess if I get something working properly I might add send a merge request to extend sp-request :)
Thank you again for all your help with this @s-KaiNet, much appreciated!

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants