Save rating data to another database field
This maintains the old behavior while also writing rating result to another field in the database.master
commit
d2f9f5f18f
|
@ -341,14 +341,17 @@ If this is a concern,
|
|||
in conjunction with ease.js'
|
||||
@url{https://www.gnu.org/software/easejs/manual/easejs.html#Type-Checks-and-Polymorphism,@samp{Class.isA}}.
|
||||
|
||||
Interfaces do not exist at runtime in TypeScript,
|
||||
but they do in easejs.
|
||||
Consequently,
|
||||
you can continue to export an ease.js interface while also exporting
|
||||
a TypeScript interface.
|
||||
Often times you will need to reference a class or interface as a
|
||||
dependency before it has been migrated away from ease.js.
|
||||
To do this,
|
||||
continue to export using @samp{module.exports} rather than
|
||||
TypeScript's @samp{export =}.
|
||||
create a corresponding @code{.d.ts} file in the same directory
|
||||
as the dependency.
|
||||
For example,
|
||||
if a class @code{Foo} is contained in @file{Foo.js},
|
||||
create a sibling @file{Foo.d.ts} file.
|
||||
For more information,
|
||||
see @url{https://www.typescriptlang.org/docs/handbook/declaration-files/introduction.html,Declaration Files}
|
||||
in the TypeScript handbook.
|
||||
|
||||
ease.js implements stackable Scala-like traits.
|
||||
Traits are @emph{not} provided by TypeScript.
|
||||
|
@ -446,7 +449,7 @@ This can be done using
|
|||
@verbatim
|
||||
type PositiveInteger = NominalType<number, 'PositiveInteger'>;
|
||||
|
||||
const isPositiveInteger = ( x: number ): n is PositiveInteger => n > 0;
|
||||
const isPositiveInteger = ( n: number ): n is PositiveInteger => n > 0;
|
||||
|
||||
const lookupIndex<T>( arr: T[], i: PositiveInteger ): T => arr[ i ];
|
||||
|
||||
|
|
|
@ -0,0 +1,39 @@
|
|||
/**
|
||||
* Representation of actions to be performed by the client
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* Action to be performed by the client
|
||||
*
|
||||
* TODO: More specific types
|
||||
*/
|
||||
export interface ClientAction
|
||||
{
|
||||
/** Action to be performed */
|
||||
action: string;
|
||||
|
||||
/** Action arguments */
|
||||
[P: string]: any;
|
||||
}
|
||||
|
||||
|
||||
/** Set of actions */
|
||||
export type ClientActions = ClientAction[];
|
|
@ -0,0 +1,43 @@
|
|||
/**
|
||||
* Numeric types
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* TypeScript's type system does not support algebraic numeric domains. A
|
||||
* compromise is to provide nominal types that allow developers to assume
|
||||
* that some constraint has been met, and then ensure that the type is only
|
||||
* ever asserted when that constraint is explicitly validated at
|
||||
* runtime. This allows us to have compile-time checks on numeric values
|
||||
* under the assumption that the runtime will enforce them.
|
||||
*
|
||||
* For this to work, _it is important to always use type predicates_;
|
||||
* if you explicit cast to one of these numeric types, it circumvents the
|
||||
* safety provided by the system and may introduce nasty bugs, since users
|
||||
* of these types assume the provided data has already been validated.
|
||||
*/
|
||||
|
||||
/**
|
||||
* Any number ≥ 0
|
||||
*
|
||||
* This is useful for array indexing.
|
||||
*/
|
||||
export type PositiveInteger = NominalType<number, 'PositiveInteger'>;
|
||||
|
||||
|
||||
/** Whether the given number is suitable as a PositiveInteger */
|
||||
export const isPositiveInteger = ( n: number ): n is PositiveInteger => n >= 0;
|
|
@ -0,0 +1,27 @@
|
|||
/**
|
||||
* Contains Program base class
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
export declare abstract class Program
|
||||
{
|
||||
readonly ineligibleLockCount: number;
|
||||
|
||||
getId(): string;
|
||||
}
|
|
@ -0,0 +1,93 @@
|
|||
/**
|
||||
* Contains program Quote class
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @todo Use ``document'' terminology in place of ``quote''
|
||||
*/
|
||||
|
||||
import { Program } from "../program/Program";
|
||||
import { Quote, QuoteId } from "./Quote";
|
||||
|
||||
|
||||
export declare class BaseQuote implements Quote
|
||||
{
|
||||
/**
|
||||
* Retrieve Program associated with quote
|
||||
*
|
||||
* @return quote program
|
||||
*/
|
||||
getProgram(): Program;
|
||||
|
||||
|
||||
/**
|
||||
* Returns the program id associated with the quote
|
||||
*
|
||||
* @return program id
|
||||
*/
|
||||
getProgramId(): string;
|
||||
|
||||
|
||||
/**
|
||||
* Returns the quote id
|
||||
*
|
||||
* The quote id is immutable. A different quote id would represent a
|
||||
* different quote, therefore a new object should be created with the
|
||||
* desired quote id.
|
||||
*
|
||||
* @return quote id
|
||||
*/
|
||||
getId(): QuoteId;
|
||||
|
||||
|
||||
/**
|
||||
* Returns the id of the current step
|
||||
*
|
||||
* @return id of current step
|
||||
*/
|
||||
getCurrentStepId(): number;
|
||||
|
||||
|
||||
/**
|
||||
* Sets an explicit lock, providing a reason for doing so
|
||||
*
|
||||
* @param reason - lock reason
|
||||
* @param step - step that user may not navigate prior
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
setExplicitLock( reason: string, step: number ): this;
|
||||
|
||||
|
||||
/**
|
||||
* Set the date that the premium was calculated as a Unix timestamp
|
||||
*
|
||||
* @param timestamp - Unix timestamp representing premium date
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
setLastPremiumDate( timestamp: UnixTimestamp ): this;
|
||||
|
||||
|
||||
/**
|
||||
* Retrieve the last time the premium was calculated
|
||||
*
|
||||
* @return last calculated time or 0
|
||||
*/
|
||||
getLastPremiumDate(): UnixTimestamp;
|
||||
}
|
|
@ -0,0 +1,33 @@
|
|||
/**
|
||||
* Generic interface to represent quotes
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @todo Use ``document'' terminology in place of ``quote''
|
||||
*/
|
||||
|
||||
import { Program } from "../program/Program";
|
||||
import { QuoteId } from "../document/Document";
|
||||
|
||||
|
||||
export declare interface Quote
|
||||
{
|
||||
// TODO: the easejs interface is empty; is this actually needed?
|
||||
}
|
||||
|
||||
export { QuoteId };
|
|
@ -0,0 +1,66 @@
|
|||
/**
|
||||
* General server actions
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { ClientActions } from "../client/action/ClientAction";
|
||||
import { ServerSideQuote } from "./quote/ServerSideQuote";
|
||||
import { UserRequest } from "./request/UserRequest";
|
||||
|
||||
|
||||
/**
|
||||
* General server actions
|
||||
*/
|
||||
export declare class Server
|
||||
{
|
||||
/**
|
||||
* Send response to user
|
||||
*
|
||||
* @param request - request to respond to
|
||||
* @param quote - quote associated with request
|
||||
* @param data - data with which to reply
|
||||
* @param actions - optional client actions
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
sendResponse(
|
||||
request: UserRequest,
|
||||
quote: ServerSideQuote,
|
||||
data: Record<string, any>,
|
||||
actions?: ClientActions,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Send response to user
|
||||
*
|
||||
* @param request - request to respond to
|
||||
* @param message - message to display to user
|
||||
* @param actions - optional client actions
|
||||
* @param btn_caption - optional caption for acknowledgement button
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
sendError(
|
||||
request: UserRequest,
|
||||
message: string,
|
||||
actions?: ClientActions,
|
||||
btn_caption?: string,
|
||||
): this;
|
||||
}
|
|
@ -28,6 +28,8 @@ const {
|
|||
ReplSetServers: ReplSetServers,
|
||||
} = require( 'mongodb/lib/mongodb' );
|
||||
|
||||
const easejs = require( 'easejs' );
|
||||
|
||||
const regex_base = /^\/quote\/([a-z0-9-]+)\/?(?:\/(\d+)\/?(?:\/(.*))?|\/(program.js))?$/;
|
||||
const regex_step = /^step\/(\d+)\/?(?:\/(post|visit))?$/;
|
||||
|
||||
|
@ -83,9 +85,8 @@ const {
|
|||
ExportService,
|
||||
},
|
||||
|
||||
RatingService,
|
||||
RatingService: { RatingService },
|
||||
RatingServicePublish,
|
||||
RatingServiceSubmitNotify,
|
||||
TokenedService,
|
||||
},
|
||||
|
||||
|
@ -137,7 +138,7 @@ exports.init = function( logger, enc_service, conf )
|
|||
server.init( server_cache, exports.rater );
|
||||
|
||||
// TODO: temporary proof-of-concept
|
||||
rating_service = RatingService.use(
|
||||
rating_service = easejs( RatingService ).use(
|
||||
RatingServicePublish( amqplib, exports.post_rate_publish, logger )
|
||||
)(
|
||||
logger, dao, server, exports.rater
|
||||
|
@ -535,11 +536,9 @@ function doRoute( program, request, data, resolve, reject )
|
|||
{
|
||||
var response = UserResponse( request );
|
||||
|
||||
rating_service.request( request, response, quote, alias, function()
|
||||
{
|
||||
// we're done; free the lock
|
||||
free();
|
||||
} );
|
||||
rating_service.request( request, response, quote, alias )
|
||||
.catch( () => {} )
|
||||
.then( () => free() );
|
||||
} );
|
||||
}, true );
|
||||
}
|
||||
|
|
|
@ -0,0 +1,145 @@
|
|||
/**
|
||||
* Mongo DB DAO for program server
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { ServerDao, Callback } from "./ServerDao";
|
||||
|
||||
import { ClassificationData, WorksheetData } from "../rater/Rater";
|
||||
import { PositiveInteger } from "../../numeric";
|
||||
import { QuoteId } from "../../document/Document";
|
||||
import { ServerSideQuote } from "../quote/ServerSideQuote";
|
||||
|
||||
|
||||
/**
|
||||
* MongoDB-backed data store
|
||||
*/
|
||||
export declare class MongoServerDao implements ServerDao
|
||||
{
|
||||
/**
|
||||
* Saves a quote to the database
|
||||
*
|
||||
* A full save will include all metadata.
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
* @param save_data - quote data to save (optional)
|
||||
*/
|
||||
saveQuote(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
save_data: Record<string, any>,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Merges bucket data with the existing bucket (rather than overwriting the
|
||||
* entire bucket)
|
||||
*
|
||||
* @param quote - quote to save
|
||||
* @param data - bucket data
|
||||
* @param success - successful callback
|
||||
* @param failure - failure callback
|
||||
*/
|
||||
mergeBucket(
|
||||
quote: ServerSideQuote,
|
||||
data: Record<string, any>,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Save quote classification data
|
||||
*
|
||||
* @param quote - quote to save
|
||||
* @param classes - classification data
|
||||
* @param success - successful callback
|
||||
* @param failure - failure callback
|
||||
*/
|
||||
saveQuoteClasses(
|
||||
quote: ServerSideQuote,
|
||||
classes: ClassificationData,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Saves the quote state to the database
|
||||
*
|
||||
* The quote state includes the current step, the top visited step and the
|
||||
* explicit lock message.
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
*/
|
||||
saveQuoteState(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Saves the quote lock state to the database
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
*/
|
||||
saveQuoteLockState(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this
|
||||
|
||||
|
||||
/**
|
||||
* Save worksheet data
|
||||
*
|
||||
* @param qid - quote identifier
|
||||
* @param data - worksheet data
|
||||
* @param callback - callback
|
||||
*/
|
||||
setWorksheets(
|
||||
qid: QuoteId,
|
||||
data: WorksheetData,
|
||||
callback: NodeCallback<void>,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Retrieve worksheet data
|
||||
*
|
||||
* @param qid - quote identifier
|
||||
* @param supplier - supplier id
|
||||
* @param index - worksheet index
|
||||
* @param callback - callback
|
||||
*/
|
||||
getWorksheet(
|
||||
qid: QuoteId,
|
||||
supplier: string,
|
||||
index: PositiveInteger,
|
||||
callback: ( data: WorksheetData | null ) => void,
|
||||
): this;
|
||||
}
|
|
@ -0,0 +1,149 @@
|
|||
/**
|
||||
* General server database operations
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* This interface was created to satisfy MongoServerDao and may not be
|
||||
* sufficiently general for other database abstractions.
|
||||
*/
|
||||
|
||||
import { ClassificationData, WorksheetData } from "../rater/Rater";
|
||||
import { PositiveInteger } from "../../numeric";
|
||||
import { QuoteId } from "../../document/Document";
|
||||
import { ServerSideQuote } from "../quote/ServerSideQuote";
|
||||
|
||||
/** Success or failure callback */
|
||||
export type Callback = ( quote: ServerSideQuote ) => void;
|
||||
|
||||
|
||||
/**
|
||||
* Database abstraction
|
||||
*/
|
||||
export interface ServerDao
|
||||
{
|
||||
/**
|
||||
* Saves a quote to the database
|
||||
*
|
||||
* A full save will include all metadata.
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
* @param save_data - quote data to save (optional)
|
||||
*/
|
||||
saveQuote(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
save_data: Record<string, any>,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Merges bucket data with the existing bucket (rather than overwriting the
|
||||
* entire bucket)
|
||||
*
|
||||
* @param quote - quote to save
|
||||
* @param data - bucket data
|
||||
* @param success - successful callback
|
||||
* @param failure - failure callback
|
||||
*/
|
||||
mergeBucket(
|
||||
quote: ServerSideQuote,
|
||||
data: Record<string, any>,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Save quote classification data
|
||||
*
|
||||
* @param quote - quote to save
|
||||
* @param classes - classification data
|
||||
* @param success - successful callback
|
||||
* @param failure - failure callback
|
||||
*/
|
||||
saveQuoteClasses(
|
||||
quote: ServerSideQuote,
|
||||
classes: ClassificationData,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Saves the quote state to the database
|
||||
*
|
||||
* The quote state includes the current step, the top visited step and the
|
||||
* explicit lock message.
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
*/
|
||||
saveQuoteState(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Saves the quote lock state to the database
|
||||
*
|
||||
* @param quote - the quote to save
|
||||
* @param success - function to call on success
|
||||
* @param failure - function to call if save fails
|
||||
*/
|
||||
saveQuoteLockState(
|
||||
quote: ServerSideQuote,
|
||||
success: Callback,
|
||||
failure: Callback,
|
||||
): this
|
||||
|
||||
|
||||
/**
|
||||
* Save worksheet data
|
||||
*
|
||||
* @param qid - quote identifier
|
||||
* @param data - worksheet data
|
||||
* @param callback - callback
|
||||
*/
|
||||
setWorksheets(
|
||||
qid: QuoteId,
|
||||
data: WorksheetData,
|
||||
callback: NodeCallback<void>,
|
||||
): this;
|
||||
|
||||
|
||||
/**
|
||||
* Retrieve worksheet data
|
||||
*
|
||||
* @param qid - quote identifier
|
||||
* @param supplier - supplier id
|
||||
* @param index - worksheet index
|
||||
* @param callback - callback
|
||||
*/
|
||||
getWorksheet(
|
||||
qid: QuoteId,
|
||||
supplier: string,
|
||||
index: PositiveInteger,
|
||||
callback: ( data: WorksheetData | null ) => void,
|
||||
): this;
|
||||
}
|
|
@ -0,0 +1,45 @@
|
|||
/**
|
||||
* Priority log typescript type definitions
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
export declare interface PriorityLog
|
||||
{
|
||||
readonly PRIORITY_ERROR: number;
|
||||
readonly PRIORITY_IMPORTANT: number;
|
||||
readonly PRIORITY_DB: number;
|
||||
readonly PRIORITY_INFO: number;
|
||||
readonly PRIORITY_SOCKET: number;
|
||||
|
||||
/**
|
||||
* Write to the log at the given priority
|
||||
*
|
||||
* If the priority is less than or equal to the set priority for this
|
||||
* object, it will be logged. Otherwise, the message will be ignored.
|
||||
*
|
||||
* The first argument should be the priority. The remaining arguments should
|
||||
* be provided in a sprintf()-style fashion
|
||||
*
|
||||
* @param priority - logging priority
|
||||
* @param ...args - sprintf-style aruments
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
log( priority: number, ...args: Array<string|number> ): this;
|
||||
}
|
|
@ -0,0 +1,46 @@
|
|||
/**
|
||||
* Augments a quote with additional data for use by the quote server
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU General Public License as published by
|
||||
* the Free Software Foundation, either version 3 of the License, or
|
||||
* (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*
|
||||
* @todo Use ``document'' terminology in place of ``quote''
|
||||
*/
|
||||
|
||||
import { Program } from "../../program/Program";
|
||||
import { BaseQuote } from "../../quote/BaseQuote";
|
||||
|
||||
|
||||
export declare class ServerSideQuote extends BaseQuote
|
||||
{
|
||||
/**
|
||||
* Last rated date, if any
|
||||
*
|
||||
* @return last rated date
|
||||
*/
|
||||
getRatedDate(): UnixTimestamp;
|
||||
|
||||
|
||||
/**
|
||||
* Set the timestamp of the first time quote was rated
|
||||
*
|
||||
* @param timestamp - Unix timestamp representing first rated date
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
setRatedDate( timestamp: UnixTimestamp ): this;
|
||||
}
|
|
@ -20,7 +20,6 @@
|
|||
*/
|
||||
|
||||
var Class = require( 'easejs' ).Class,
|
||||
Rater = require( './Rater' ),
|
||||
EventEmitter = require( 'events' ).EventEmitter,
|
||||
|
||||
DslRaterContext = require( './DslRaterContext' );
|
||||
|
|
|
@ -20,7 +20,6 @@
|
|||
*/
|
||||
|
||||
var Class = require( 'easejs' ).Class,
|
||||
Rater = require( './Rater' ),
|
||||
EventEmitter = require( 'events' ).EventEmitter,
|
||||
Quote = require( '../../quote/Quote' );
|
||||
|
||||
|
|
|
@ -22,18 +22,14 @@
|
|||
* "HttpRater"
|
||||
*/
|
||||
|
||||
var Class = require( 'easejs' ).Class,
|
||||
Rater = require( './Rater' ),
|
||||
|
||||
querystring = require( 'querystring' )
|
||||
;
|
||||
var Class = require( 'easejs' ).Class;
|
||||
var querystring = require( 'querystring' );
|
||||
|
||||
|
||||
/**
|
||||
* Rates using one of the PHP raters
|
||||
*/
|
||||
module.exports = Class( 'HttpRater' )
|
||||
.implement( Rater )
|
||||
.extend(
|
||||
{
|
||||
/**
|
||||
|
|
|
@ -0,0 +1,35 @@
|
|||
/**
|
||||
* Rating process manager
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { Rater } from "./Rater";
|
||||
|
||||
|
||||
export declare class ProcessManager
|
||||
{
|
||||
/**
|
||||
* Returns the rater associated with the given id
|
||||
*
|
||||
* @param id - rater id
|
||||
*
|
||||
* @return requested rater
|
||||
*/
|
||||
byId( id: string ): Rater;
|
||||
}
|
|
@ -69,6 +69,9 @@ const _signum = {
|
|||
*
|
||||
* Handles formatting and sending requests to the rating process; and
|
||||
* processing replies.
|
||||
*
|
||||
* TODO: Rename this class and provide a more generic interface. The caller
|
||||
* does not care that this sends data to another process for rating.
|
||||
*/
|
||||
module.exports = Class( 'ProcessManager',
|
||||
{
|
||||
|
|
|
@ -0,0 +1,121 @@
|
|||
/**
|
||||
* Contains Rater interface
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
import { ClientActions } from "../../client/action/ClientAction";
|
||||
import { ServerSideQuote } from "../quote/ServerSideQuote";
|
||||
import { UserSession } from "../request/UserSession";
|
||||
|
||||
|
||||
|
||||
/** Result of rating */
|
||||
export interface RateResult
|
||||
{
|
||||
/** Whether all suppliers were not able to provide rates */
|
||||
_unavailable_all: '0' | '1';
|
||||
|
||||
/** Result data */
|
||||
[P: string]: any;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Result of rating with an individual supplier
|
||||
*
|
||||
* This gets combined into a single RateResult prefixed with each supplier
|
||||
* id and an underscore.
|
||||
*/
|
||||
export interface SupplierRateResult
|
||||
{
|
||||
/** Rating worksheet data */
|
||||
__worksheet?: WorksheetData,
|
||||
|
||||
/** Classification system results */
|
||||
__classes?: ClassificationData,
|
||||
|
||||
/** Basic profiling data */
|
||||
__perf: PerformanceData,
|
||||
|
||||
/** Ineligible message, if any */
|
||||
ineligible: string,
|
||||
|
||||
/** Submit message, if any */
|
||||
submit: string,
|
||||
|
||||
/** Final premium */
|
||||
premium: number,
|
||||
|
||||
/** Rating data */
|
||||
[P: string]: any;
|
||||
}
|
||||
|
||||
|
||||
/** Basic profiling data */
|
||||
export interface PerformanceData
|
||||
{
|
||||
/** Timestamp of beginning of rating */
|
||||
start: UnixTimestampMillis;
|
||||
|
||||
/** Timestamp of end of rating */
|
||||
end: UnixTimestampMillis;
|
||||
|
||||
/** Total rating time */
|
||||
total: Milliseconds;
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* Worksheet data from rater
|
||||
*
|
||||
* These data come from the compiled raters.
|
||||
*
|
||||
* TODO: Fill in a schema here
|
||||
*/
|
||||
export type WorksheetData = Record<string, any>;
|
||||
|
||||
|
||||
/** Classification results */
|
||||
export type ClassificationData = Record<string, boolean>;
|
||||
|
||||
|
||||
/**
|
||||
* Represents a rater that will generate a quote from a given set of values
|
||||
*/
|
||||
export interface Rater
|
||||
{
|
||||
/**
|
||||
* Asynchronously performs rating
|
||||
*
|
||||
* @param quote - quote to perform rating on
|
||||
* @param session - user session
|
||||
* @param indv - individual supplier to rate (otherwise empty)
|
||||
* @param success - continuation when rating is successful
|
||||
* @param failure - continuation when rating fails
|
||||
*
|
||||
* @return self
|
||||
*/
|
||||
rate(
|
||||
quote: ServerSideQuote,
|
||||
session: UserSession,
|
||||
indv: string,
|
||||
success: ( rate_data: RateResult, actions: ClientActions ) => void,
|
||||
failure: ( message: string ) => void,
|
||||
): this;
|
||||
}
|
|
@ -1,5 +1,5 @@
|
|||
/**
|
||||
* Contains Rater interface
|
||||
* User request abstraction
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
|
@ -19,22 +19,18 @@
|
|||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
var Interface = require( 'easejs' ).Interface;
|
||||
import { UserSession } from "./UserSession";
|
||||
|
||||
|
||||
/**
|
||||
* Represents a rater that will generate a quote from a given set of values
|
||||
* Representation of request from user
|
||||
*/
|
||||
module.exports = Interface( 'Rater',
|
||||
export declare class UserRequest
|
||||
{
|
||||
/**
|
||||
* Asynchronously performs rating using the data from the given bucket
|
||||
* Retrieve the current session
|
||||
*
|
||||
* @param {Quote} quote to rate
|
||||
* @param {function()} callback function to call when complete
|
||||
*
|
||||
* @return {Rater} self
|
||||
* @return current session
|
||||
*/
|
||||
'public rate': [ 'quote', 'args', 'callback' ],
|
||||
} );
|
||||
|
||||
getSession(): UserSession;
|
||||
}
|
|
@ -0,0 +1,28 @@
|
|||
/**
|
||||
* UserResponse class
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* Manipulates response to user request
|
||||
*/
|
||||
export declare class UserResponse
|
||||
{
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
/**
|
||||
* UserSession class
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
|
||||
/**
|
||||
* Session management
|
||||
*/
|
||||
export declare class UserSession
|
||||
{
|
||||
/**
|
||||
* Whether the user is logged in as an internal user
|
||||
*
|
||||
* @return true if internal user, otherwise false
|
||||
*/
|
||||
isInternal(): boolean;
|
||||
}
|
|
@ -1,420 +0,0 @@
|
|||
/**
|
||||
* Rating service
|
||||
*
|
||||
* Copyright (C) 2010-2019 R-T Specialty, LLC.
|
||||
*
|
||||
* This file is part of the Liza Data Collection Framework.
|
||||
*
|
||||
* liza is free software: you can redistribute it and/or modify
|
||||
* it under the terms of the GNU Affero General Public License as
|
||||
* published by the Free Software Foundation, either version 3 of the
|
||||
* License, or (at your option) any later version.
|
||||
*
|
||||
* This program is distributed in the hope that it will be useful,
|
||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
||||
* GNU General Public License for more details.
|
||||
*
|
||||
* You should have received a copy of the GNU Affero General Public License
|
||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
||||
*/
|
||||
|
||||
var Class = require( 'easejs' ).Class;
|
||||
|
||||
|
||||
/**
|
||||
* XXX: Half-assed, quick refactoring to extract from Server class; this is not
|
||||
* yet complete!
|
||||
*
|
||||
* TODO: Logging should be implemented by observers
|
||||
*/
|
||||
module.exports = Class( 'RatingService',
|
||||
{
|
||||
logger: null,
|
||||
|
||||
dao: null,
|
||||
|
||||
_server: null,
|
||||
|
||||
_raters: null,
|
||||
|
||||
|
||||
__construct: function( logger, dao, server, raters )
|
||||
{
|
||||
this._logger = logger;
|
||||
this._dao = dao;
|
||||
this._server = server;
|
||||
this._raters = raters;
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Sends rates to the client
|
||||
*
|
||||
* Note that the continuation will be called after all data saving is
|
||||
* complete; the request will be sent back to the client before then.
|
||||
*
|
||||
* @param {UserRequest} request user request to satisfy
|
||||
* @param {UserResponse} response pending response
|
||||
* @param {Quote} quote quote to export
|
||||
* @param {string} cmd applicable of command request
|
||||
* @param {Function} callback continuation after saving is complete
|
||||
*
|
||||
* @return Server self to allow for method chaining
|
||||
*/
|
||||
'public request': function( request, response, quote, cmd, callback )
|
||||
{
|
||||
// cmd represents a request for a single rater
|
||||
if ( !cmd && this._isQuoteValid( quote ) )
|
||||
{
|
||||
// send an empty reply (keeps what is currently in the bucket)
|
||||
this._server.sendResponse( request, quote, {
|
||||
data: {},
|
||||
}, [] );
|
||||
|
||||
callback();
|
||||
return this;
|
||||
}
|
||||
|
||||
var program = quote.getProgram();
|
||||
|
||||
try
|
||||
{
|
||||
this._performRating( request, program, quote, cmd, callback );
|
||||
}
|
||||
catch ( err )
|
||||
{
|
||||
this._sendRatingError( request, quote, program, err );
|
||||
callback();
|
||||
}
|
||||
|
||||
return this;
|
||||
},
|
||||
|
||||
|
||||
_getProgramRater: function( program, quote )
|
||||
{
|
||||
var rater = this._raters.byId( program.getId() );
|
||||
|
||||
// if a rater could not be found, we can't do any rating
|
||||
if ( rater === null )
|
||||
{
|
||||
this._logger.log( this._logger.PRIORITY_ERROR,
|
||||
"Rating for quote %d (program %s) failed; missing module",
|
||||
quote.getId(),
|
||||
program.getId()
|
||||
);
|
||||
}
|
||||
|
||||
return rater;
|
||||
},
|
||||
|
||||
|
||||
_isQuoteValid: function( quote )
|
||||
{
|
||||
// quotes are valid for 30 days
|
||||
var re_date = Math.round( ( ( new Date() ).getTime() / 1000 ) -
|
||||
( 60 * 60 * 24 * 30 )
|
||||
);
|
||||
|
||||
if ( quote.getLastPremiumDate() > re_date )
|
||||
{
|
||||
this._logger.log( this._logger.PRIORITY_INFO,
|
||||
"Skipping '%s' rating for quote #%s; quote is still valid",
|
||||
quote.getProgramId(),
|
||||
quote.getId()
|
||||
);
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
},
|
||||
|
||||
|
||||
_performRating: function( request, program, quote, indv, c )
|
||||
{
|
||||
var _self = this;
|
||||
|
||||
var rater = this._getProgramRater( program );
|
||||
if ( !rater )
|
||||
{
|
||||
this._server.sendError( request, 'Unable to perform rating.' );
|
||||
c();
|
||||
}
|
||||
|
||||
this._logger.log( this._logger.PRIORITY_INFO,
|
||||
"Performing '%s' rating for quote #%s",
|
||||
quote.getProgramId(),
|
||||
quote.getId()
|
||||
);
|
||||
|
||||
rater.rate( quote, request.getSession(), indv,
|
||||
function( rate_data, actions )
|
||||
{
|
||||
actions = actions || [];
|
||||
|
||||
_self.postProcessRaterData(
|
||||
request, rate_data, actions, program, quote
|
||||
);
|
||||
|
||||
const class_dest = {};
|
||||
|
||||
const cleaned = _self._cleanRateData(
|
||||
rate_data,
|
||||
class_dest
|
||||
);
|
||||
|
||||
// TODO: move me during refactoring
|
||||
_self._dao.saveQuoteClasses( quote, class_dest );
|
||||
|
||||
// save all data server-side (important: do after
|
||||
// post-processing); async
|
||||
_self._saveRatingData( quote, rate_data, indv, function()
|
||||
{
|
||||
// we're done
|
||||
c();
|
||||
} );
|
||||
|
||||
// no need to wait for the save; send the response
|
||||
_self._server.sendResponse( request, quote, {
|
||||
data: cleaned,
|
||||
initialRatedDate: quote.getRatedDate(),
|
||||
lastRatedDate: quote.getLastPremiumDate()
|
||||
}, actions );
|
||||
},
|
||||
function( message )
|
||||
{
|
||||
_self._sendRatingError( request, quote, program,
|
||||
Error( message )
|
||||
);
|
||||
|
||||
c();
|
||||
}
|
||||
);
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Saves rating data
|
||||
*
|
||||
* Data will be merged with existing bucket data and saved. The idea behind
|
||||
* this is to allow us to reference the data (e.g. for reporting) even if
|
||||
* the client does not save it.
|
||||
*
|
||||
* @param {Quote} quote quote to save data to
|
||||
* @param {Object} data rating data
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
_saveRatingData: function( quote, data, indv, c )
|
||||
{
|
||||
// only update the last premium calc date on the initial request
|
||||
if ( !indv )
|
||||
{
|
||||
var cur_date = Math.round(
|
||||
( new Date() ).getTime() / 1000
|
||||
);
|
||||
|
||||
quote.setLastPremiumDate( cur_date );
|
||||
quote.setRatedDate( cur_date );
|
||||
|
||||
function done()
|
||||
{
|
||||
c();
|
||||
}
|
||||
|
||||
// save the last prem status (we pass an empty object as the save
|
||||
// data argument to ensure that we do not save the actual bucket
|
||||
// data, which may cause a race condition with the below merge call)
|
||||
this._dao.saveQuote( quote, done, done, {} );
|
||||
}
|
||||
else
|
||||
{
|
||||
c();
|
||||
}
|
||||
|
||||
// we're not going to worry about whether or not this fails; if it does,
|
||||
// an error will be automatically logged, but we still want to give the
|
||||
// user a rate (if this save fails, it's likely we have bigger problems
|
||||
// anyway); this can also be done concurrently with the above request
|
||||
// since it only modifies a portion of the bucket
|
||||
this._dao.mergeBucket( quote, data );
|
||||
},
|
||||
|
||||
|
||||
/**
|
||||
* Process rater data returned from a rater
|
||||
*
|
||||
* @param {UserRequest} request user request to satisfy
|
||||
* @param {Object} data rating data returned
|
||||
* @param {Array} actions actions to send to client
|
||||
* @param {Program} program program used to perform rating
|
||||
* @param {Quote} quote quote used for rating
|
||||
*
|
||||
* @return {undefined}
|
||||
*/
|
||||
'virtual protected postProcessRaterData': function(
|
||||
request, data, actions, program, quote
|
||||
)
|
||||
{
|
||||
var meta = data._cmpdata || {};
|
||||
|
||||
// the metadata will not be provided to the client
|
||||
delete data._cmpdata;
|
||||
|
||||
// rating worksheets are returned as metadata
|
||||
this._processWorksheetData( quote.getId(), data );
|
||||
|
||||
if ( ( program.ineligibleLockCount > 0 )
|
||||
&& ( +meta.count_ineligible >= program.ineligibleLockCount )
|
||||
)
|
||||
{
|
||||
// lock the quote client-side (we don't send them the reason; they
|
||||
// don't need it) to the current step
|
||||
actions.push( { action: 'lock' } );
|
||||
|
||||
var lock_reason = 'Supplier ineligibility restriction';
|
||||
var lock_step = quote.getCurrentStepId();
|
||||
|
||||
// the next step is the step that displays the rating results
|
||||
quote.setExplicitLock( lock_reason, ( lock_step + 1 ) );
|
||||
|
||||
// important: only save the lock state, not the step states, as we
|
||||
// have a race condition with async. rating (the /visit request may
|
||||
// be made while we're rating, and when we come back we would then
|
||||
// update the step id with a prior, incorrect step)
|
||||
this._dao.saveQuoteLockState( quote );
|
||||
}
|
||||
|
||||
// if any have been deferred, instruct the client to request them
|
||||
// individually
|
||||
if ( Array.isArray( meta.deferred ) && ( meta.deferred.length > 0 ) )
|
||||
{
|
||||
var torate = [];
|
||||
|
||||
meta.deferred.forEach( function( alias )
|
||||
{
|
||||
actions.push( { action: 'indvRate', id: alias } );
|
||||
torate.push( alias );
|
||||
} );
|
||||
|
||||
// we log that we're performing rating, so we should also log when
|
||||
// it is deferred (otherwise the logs will be rather confusing)
|
||||
this._logger.log( this._logger.PRIORITY_INFO,
|
||||
"'%s' rating deferred for quote #%s; will rate: %s",
|
||||
quote.getProgramId(),
|
||||
quote.getId(),
|
||||
torate.join( ',' )
|
||||
);
|
||||
}
|
||||
},
|
||||
|
||||
|
||||
_sendRatingError: function( request, quote, program, err )
|
||||
{
|
||||
// well that's no good
|
||||
this._logger.log( this._logger.PRIORITY_ERROR,
|
||||
"Rating for quote %d (program %s) failed: %s",
|
||||
quote.getId(),
|
||||
program.getId(),
|
||||
err.message + '\n-!' + err.stack.replace( /\n/g, '\n-!' )
|
||||
);
|
||||
|
||||
this._server.sendError( request,
|
||||
'There was a problem during the rating process. Unable to ' +
|
||||
'continue. Please contact our support team for assistance.' +
|
||||
|
||||
// show details for internal users
|
||||
( ( request.getSession().isInternal() )
|
||||
? '<br /><br />[Internal] ' + err.message + '<br /><br />' +
|
||||
'<hr />' + err.stack.replace( /\n/g, '<br />' )
|
||||
: ''
|
||||
)
|
||||
);
|
||||
},
|
||||
|
||||
|
||||
_processWorksheetData: function( qid, data )
|
||||
{
|
||||
// TODO: this should be done earlier on, so that this is not necessary
|
||||
var wre = /^(.+)___worksheet$/,
|
||||
worksheets = {};
|
||||
|
||||