Correct pattern for checking if a logged in user has access to a Portal item?

1256
1
04-15-2021 05:53 PM
Jay_Gregory
Occasional Contributor III

In my JS 4.x application I am using IdentityManager and OAuth (via appid/secret) to have users login to my Portal (10.8.1).  There are plenty of examples showing how to do this.  What I’m having trouble figuring out is how to then determine if a user has access to the resource (a Portal layer) that my site wants to load.  If they DO have access, I then want to load the layer onto the map, but if they don’t, then the site might do something else (like load a different layer, or change a div to say they don’t have access). So far all I’ve figured out how to do is just login (Authentication), not check if they have access to what I want them to (authorization).  I tried changing the sharing of the actual registered app item in Portal, but all Portal users can still successfully login using that app’s registered info, not just the ones I shared it with.  

Anyone have suggestions for a working pattern here?

0 Kudos
1 Reply
Jade_Freeman
Occasional Contributor

Here's some code from a VueJS app where I think we do what you are trying to do.  In the code below, we use our registered app id to get the user to log in but then also load, using PortalItem, the registered app using it's item ID.  On the ArcGIS Enterprise side, the registered app is shared with a group the user is a member of so the user should only be able to load the app if they are a member of that group.  I suppose the registered app could be replaced with any item shared with the appropriate group the user needs to be a member of but this approach seems to keep it nice and tidy and self-contained.  

Hope this helps!

import Vue from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
import vuetify from './plugins/vuetify'
import IdentityManager from '@arcgis/core/identity/IdentityManager'
import OAuthInfo from '@arcgis/core/identity/OAuthInfo'
import Portal from '@arcgis/core/portal/Portal'
import PortalItem from '@arcgis/core/portal/PortalItem'
import '@arcgis/core/assets/esri/themes/light/main.css'

Vue.config.productionTip = false

const registerdAppId = '123456789'
const portalUrl = 'https://my.arcgisenterprise/portal'
const registeredAppItemId = '987654321'

const highlightText = function (words, query) {
  if (!words) return ''

  return words.replace(new RegExp(query, 'gi'), match => {
    return '<span class=\'highlight\'>' + match + '</span>'
  })
}

const info = new OAuthInfo({
  appId: registerdAppId,
  portalUrl: portalUrl,
  popup: false
})

const esriId = IdentityManager
esriId.registerOAuthInfos([info])

const portal = new Portal({
  url: portalUrl,
  authMode: 'immediate'
})
portal
  .load()
  .then(function (results) {
    const appItem = new PortalItem({
      id: registeredAppItemId,
      portal: portal
    })
    appItem
      .load()
      .then(function (results) {
        Vue.filter('highlight', highlightText)
        new Vue({
          router,
          store,
          vuetify,
          render: h => h(App)
        }).$mount('#app')
      }, function () {
        alert('You are not authorized for this application')
      })
  })

window.addEventListener('beforeunload', (event) => {
  esriId.destroyCredentials()
})
0 Kudos