Skip to content

Commit

Permalink
fix: fixes from pr comments
Browse files Browse the repository at this point in the history
  • Loading branch information
bruuuuuuuce committed Oct 12, 2021
1 parent c037eb3 commit 732db61
Show file tree
Hide file tree
Showing 7 changed files with 112 additions and 53 deletions.
4 changes: 2 additions & 2 deletions src/GrpcErrorMapper.ts → src/CacheServiceErrorMapper.ts
Original file line number Diff line number Diff line change
@@ -1,13 +1,13 @@
import {Status} from "@grpc/grpc-js/build/src/constants";
import {ServiceError} from "@grpc/grpc-js";
import {
ClientSdkError,
CacheServiceError,
InternalServerError,
InvalidArgumentError,
PermissionDeniedError
} from './Errors';

export function errorMapper(err: ServiceError): ClientSdkError {
export function cacheServiceErrorMapper(err: ServiceError): CacheServiceError {
if (err.code === Status.PERMISSION_DENIED) {
return new PermissionDeniedError(err.message);
}
Expand Down
72 changes: 62 additions & 10 deletions src/Errors.ts
Original file line number Diff line number Diff line change
@@ -1,38 +1,90 @@
export class ClientSdkError extends Error {
/**
* Base class for all errors thrown by the sdk
*/
abstract class SdkError extends Error {
protected constructor(message: string) {
super(message);
}
}

export class ClientSdkError extends SdkError {
constructor(message: string) {
super(message);
}
}

export class CacheAlreadyExistsError extends ClientSdkError {
/**
* Represents errors thrown when invalid parameters are passed to the Momento Cache
*/
export class InvalidArgumentError extends ClientSdkError {
constructor(message: string) {
super(message);
this.name = "CacheAlreadyExistsError"
this.name = "InvalidArgumentError"
}
}

export class CacheNotFoundError extends ClientSdkError {
/**
* Gets thrown when the jwt passed to the Momento client cannot have the claims parsed
*/
export class InvalidJwtError extends ClientSdkError {
constructor(message: string) {
super(message);
this.name = "CacheNotFoundError";
this.name = "InvalidJwtError"
}
}

export class InternalServerError extends ClientSdkError {
abstract class MomentoServiceError extends SdkError {
protected constructor(message: string) {
super(message);
}
}

/**
* Base class for all exceptions resulting from Cache Service interactions
*/
export class CacheServiceError extends MomentoServiceError {
constructor(message: string) {
super(message);
this.name = "InternalServerError"
}
}

export class InvalidArgumentError extends ClientSdkError {
/**
* Error that occurs when trying to create a cache with the same name as an existing cache. To resolve this error,
* either delete the existing cache and make a new one, or change the name of the cache you are trying to create to
* one that doesn't already exist
*/
export class CacheAlreadyExistsError extends CacheServiceError {
constructor(message: string) {
super(message);
this.name = "InvalidArgumentError"
this.name = "CacheAlreadyExistsError"
}
}

/**
* Error that occurs when trying to get a cache that doesn't exist. To resolve, make sure that the cache you are trying
* to get exists. If it doesn't create it first and then try again
*/
export class CacheNotFoundError extends CacheServiceError {
constructor(message: string) {
super(message);
this.name = "CacheNotFoundError";
}
}

/**
* Cache Service encountered an unexpected exception while trying to fulfill the request
*/
export class InternalServerError extends CacheServiceError {
constructor(message: string) {
super(message);
this.name = "InternalServerError"
}
}

export class PermissionDeniedError extends ClientSdkError {
/**
* Service rejected the request as the authentication credentials presented are invalid
*/
export class PermissionDeniedError extends CacheServiceError {
constructor(message: string) {
super(message);
this.name = "PermissionDeniedError"
Expand Down
23 changes: 16 additions & 7 deletions src/Momento.ts
Original file line number Diff line number Diff line change
@@ -1,10 +1,15 @@
import {control} from '@momento/wire-types-typescript';
import jwtDecode from "jwt-decode";
import {MomentoCache} from "./MomentoCache";
import {authInterceptor} from "./grpc/AuthInterceptor";
import {InvalidArgumentError, ClientSdkError, CacheAlreadyExistsError, CacheNotFoundError} from "./Errors";
import {addHeadersInterceptor} from "./grpc/AddHeadersInterceptor";
import {
InvalidArgumentError,
CacheAlreadyExistsError,
CacheNotFoundError,
InvalidJwtError
} from "./Errors";
import {Status} from "@grpc/grpc-js/build/src/constants";
import {errorMapper} from "./GrpcErrorMapper";
import {cacheServiceErrorMapper} from "./CacheServiceErrorMapper";
import {ChannelCredentials, Interceptor} from "@grpc/grpc-js";

interface Claims {
Expand Down Expand Up @@ -34,7 +39,11 @@ export class Momento {
constructor(authToken: string, endpointOverride?: string) {
const claims = this.decodeJwt(authToken);
this.authToken = authToken;
this.interceptors = [authInterceptor(authToken)]
const headers = [{
name: 'Authorization',
value: authToken
}]
this.interceptors = [addHeadersInterceptor(headers)]
const controlEndpoint = endpointOverride ? `control.${endpointOverride}` : claims.cp;
this.cacheEndpoint = endpointOverride ? `cache.${endpointOverride}` : claims.c;
this.client = new control.control_client.ScsControlClient(controlEndpoint, ChannelCredentials.createSsl())
Expand All @@ -47,7 +56,7 @@ export class Momento {
try {
return jwtDecode<Claims>(jwt)
} catch (e) {
throw new ClientSdkError("failed to parse jwt")
throw new InvalidJwtError('failed to parse jwt')
}
}

Expand Down Expand Up @@ -75,7 +84,7 @@ export class Momento {
if (err.code === Status.ALREADY_EXISTS) {
reject(new CacheAlreadyExistsError(`cache with name: ${name} already exists`))
} else {
reject(errorMapper(err))
reject(cacheServiceErrorMapper(err))
}
} else {
resolve({})
Expand All @@ -97,7 +106,7 @@ export class Momento {
if (err.code === Status.NOT_FOUND) {
reject(new CacheNotFoundError(`cache with name: ${name} does not exist`))
} else {
reject(errorMapper(err))
reject(cacheServiceErrorMapper(err))
}
} else {
resolve({})
Expand Down
24 changes: 15 additions & 9 deletions src/MomentoCache.ts
Original file line number Diff line number Diff line change
@@ -1,9 +1,8 @@
import {cache} from '@momento/wire-types-typescript';
import {authInterceptor} from "./grpc/AuthInterceptor";
import {cacheNameInterceptor} from "./grpc/CacheNameInterceptor";
import {addHeadersInterceptor} from "./grpc/AddHeadersInterceptor";
import {momentoResultConverter} from "./messages/Result";
import {InvalidArgumentError, ClientSdkError} from "./Errors";
import {errorMapper} from "./GrpcErrorMapper";
import {InvalidArgumentError, CacheServiceError} from "./Errors";
import {cacheServiceErrorMapper} from "./CacheServiceErrorMapper";
import {ChannelCredentials, Interceptor} from "@grpc/grpc-js";
import {GetResponse} from "./messages/GetResponse";
import {SetResponse} from "./messages/SetResponse";
Expand All @@ -26,7 +25,14 @@ export class MomentoCache {
this.client = new cache.cache_client.ScsClient(endpoint, ChannelCredentials.createSsl());
this.textEncoder = new TextEncoder();
this.cacheName = cacheName;
this.interceptors = [authInterceptor(authToken), cacheNameInterceptor(cacheName)]
const headers = [{
name: 'Authorization',
value: authToken
}, {
name: 'cache',
value: cacheName
}]
this.interceptors = [addHeadersInterceptor(headers)]
}

/**
Expand Down Expand Up @@ -63,11 +69,11 @@ export class MomentoCache {
return new Promise((resolve, reject) => {
this.client.Set(request, { interceptors: this.interceptors }, (err, resp) => {
if (err) {
reject(errorMapper(err))
reject(cacheServiceErrorMapper(err))
} else if (resp) {
resolve(this.parseSetResponse(resp))
} else {
reject(new ClientSdkError("unable to perform set"))
reject(new CacheServiceError("unable to perform set"))
}
})
})
Expand Down Expand Up @@ -99,11 +105,11 @@ export class MomentoCache {
return new Promise((resolve, reject) => {
this.client.Get(request, {interceptors: this.interceptors}, (err, resp) => {
if (err) {
reject(errorMapper(err))
reject(cacheServiceErrorMapper(err))
} else if (resp) {
resolve(this.parseGetResponse(resp))
} else {
reject(new ClientSdkError("unable to get from cache"))
reject(new CacheServiceError("unable to get from cache"))
}
})
})
Expand Down
17 changes: 17 additions & 0 deletions src/grpc/AddHeadersInterceptor.ts
Original file line number Diff line number Diff line change
@@ -0,0 +1,17 @@
import {InterceptingCall, Interceptor} from "@grpc/grpc-js";

interface Header {
name: string,
value: string
}

export const addHeadersInterceptor = (headers: Header[]): Interceptor => {
return ((options, nextCall) => {
return new InterceptingCall(nextCall(options), {
start: (metadata, listener, next) => {
headers.forEach((h) => metadata.add(h.name, h.value))
next(metadata, {})
}
})
})
}
13 changes: 0 additions & 13 deletions src/grpc/AuthInterceptor.ts

This file was deleted.

12 changes: 0 additions & 12 deletions src/grpc/CacheNameInterceptor.ts

This file was deleted.

0 comments on commit 732db61

Please sign in to comment.