feat(auth-dir): break auth into three directives
@isAuthorized directive for Stream, Branch, and Commit this is a light wrapper around `authorizeResolver` which finds the `resourceId` depending on where the request is coming from. it's still not super cleand and I will continue thinking about how to improve this despite inconsistencies with the id location
This commit is contained in:
@@ -0,0 +1,29 @@
|
||||
const { ApolloError, ForbiddenError, SchemaDirectiveVisitor } = require( 'apollo-server-express' )
|
||||
const { defaultFieldResolver } = require( 'graphql' )
|
||||
const appRoot = require( 'app-root-path' )
|
||||
const { authorizeResolver } = require( `${appRoot}/modules/shared` )
|
||||
|
||||
module.exports = {
|
||||
isAuthorizedForStream: class IsAuthorizedForStreamDirective extends SchemaDirectiveVisitor {
|
||||
visitFieldDefinition( field ) {
|
||||
const { resolver = field.resolve || defaultFieldResolver, name } = field
|
||||
const requiredRole = this.args.role
|
||||
let resourceId
|
||||
|
||||
field.resolve = async function ( parent, args, context, info ) {
|
||||
if ( info.parentType == 'Subscription' ) {
|
||||
resourceId = ( parent[ name ].streamId || parent[ name ].id )
|
||||
} else {
|
||||
resourceId = args.branch.streamId
|
||||
}
|
||||
|
||||
if ( !resourceId ) throw new ApolloError( 'Could not find the resource id' )
|
||||
|
||||
await authorizeResolver( context.userId, resourceId, requiredRole )
|
||||
|
||||
const data = await resolver.call( this, parent, args, context, info )
|
||||
return data
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
const { ApolloError, ForbiddenError, SchemaDirectiveVisitor } = require( 'apollo-server-express' )
|
||||
const { defaultFieldResolver } = require( 'graphql' )
|
||||
const appRoot = require( 'app-root-path' )
|
||||
const { authorizeResolver } = require( `${appRoot}/modules/shared` )
|
||||
|
||||
module.exports = {
|
||||
isAuthorizedForStream: class IsAuthorizedForStreamDirective extends SchemaDirectiveVisitor {
|
||||
visitFieldDefinition( field ) {
|
||||
const { resolver = field.resolve || defaultFieldResolver, name } = field
|
||||
const requiredRole = this.args.role
|
||||
let resourceId
|
||||
|
||||
field.resolve = async function ( parent, args, context, info ) {
|
||||
if ( info.parentType == 'Subscription' ) {
|
||||
resourceId = ( parent[ name ].streamId || parent[ name ].id )
|
||||
} else {
|
||||
resourceId = args.commit.streamId
|
||||
}
|
||||
|
||||
if ( !resourceId ) throw new ApolloError( 'Could not find the resource id' )
|
||||
|
||||
await authorizeResolver( context.userId, resourceId, requiredRole )
|
||||
|
||||
const data = await resolver.call( this, parent, args, context, info )
|
||||
return data
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -0,0 +1,29 @@
|
||||
const { ApolloError, ForbiddenError, SchemaDirectiveVisitor } = require( 'apollo-server-express' )
|
||||
const { defaultFieldResolver } = require( 'graphql' )
|
||||
const appRoot = require( 'app-root-path' )
|
||||
const { authorizeResolver } = require( `${appRoot}/modules/shared` )
|
||||
|
||||
module.exports = {
|
||||
isAuthorizedForStream: class IsAuthorizedForStreamDirective extends SchemaDirectiveVisitor {
|
||||
visitFieldDefinition( field ) {
|
||||
const { resolver = field.resolve || defaultFieldResolver, name } = field
|
||||
const requiredRole = this.args.role
|
||||
let resourceId
|
||||
|
||||
field.resolve = async function ( parent, args, context, info ) {
|
||||
if ( info.parentType == 'Subscription' ) {
|
||||
resourceId = ( parent[ name ].streamId || parent[ name ].id )
|
||||
} else {
|
||||
resourceId = ( args.id || args.streamId || args.stream.id )
|
||||
}
|
||||
|
||||
if ( !resourceId ) throw new ApolloError( 'Could not find the resource id' )
|
||||
|
||||
await authorizeResolver( context.userId, resourceId, requiredRole )
|
||||
|
||||
const data = await resolver.call( this, parent, args, context, info )
|
||||
return data
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user