coverted to typescript and imported from eo project.
todo: fix api calls to CA
This commit is contained in:
parent
0fd5b2ec6a
commit
b95d2a2a81
31
.eslintrc.cjs
Normal file
31
.eslintrc.cjs
Normal file
@ -0,0 +1,31 @@
|
||||
/* eslint-env node */
|
||||
require("@rushstack/eslint-patch/modern-module-resolution");
|
||||
|
||||
module.exports = {
|
||||
root: true,
|
||||
extends: [
|
||||
"plugin:vue/vue3-essential",
|
||||
"plugin:vue/vue3-strongly-recommended",
|
||||
"plugin:vue/vue3-recommended",
|
||||
"eslint:recommended",
|
||||
"plugin:@typescript-eslint/recommended-type-checked",
|
||||
"@vue/eslint-config-typescript",
|
||||
"@vue/eslint-config-prettier/skip-formatting",
|
||||
],
|
||||
parser: "vue-eslint-parser",
|
||||
parserOptions: {
|
||||
ecmaVersion: "latest",
|
||||
project: ["./tsconfig.json"],
|
||||
tsconfigRootDir: __dirname,
|
||||
parser: "@typescript-eslint/parser",
|
||||
},
|
||||
rules: {
|
||||
"@typescript-eslint/no-unused-vars": [
|
||||
"warn",
|
||||
{
|
||||
argsIgnorePattern: "^_+$",
|
||||
},
|
||||
],
|
||||
},
|
||||
ignorePatterns: ["/*", "!/src"],
|
||||
};
|
||||
@ -8,6 +8,12 @@
|
||||
/>
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
|
||||
<title>Channel Automation Vue Apps</title>
|
||||
<script>
|
||||
function resizeIframe(obj) {
|
||||
obj.style.height =
|
||||
obj.contentWindow.document.documentElement.scrollHeight + "px";
|
||||
}
|
||||
</script>
|
||||
</head>
|
||||
<body>
|
||||
<div id="app"></div>
|
||||
|
||||
3084
package-lock.json
generated
3084
package-lock.json
generated
File diff suppressed because it is too large
Load Diff
20
package.json
20
package.json
@ -7,21 +7,33 @@
|
||||
"dev": "vite",
|
||||
"build": "vue-tsc && vite build",
|
||||
"preview": "vite preview",
|
||||
"lint": "eslint --ext .js,.vue --ignore-path .gitignore --fix src",
|
||||
"lint": "eslint --ext .ts,.vue --ignore-path .gitignore --fix src",
|
||||
"format": "prettier . --write"
|
||||
},
|
||||
"dependencies": {
|
||||
"eslint": "^8.51.0",
|
||||
"eslint-plugin-vue": "^9.17.0",
|
||||
"prettier": "^3.0.3",
|
||||
"@fortawesome/fontawesome-svg-core": "^6.5.1",
|
||||
"@fortawesome/free-solid-svg-icons": "^6.5.1",
|
||||
"@fortawesome/vue-fontawesome": "^3.0.5",
|
||||
"@rushstack/eslint-patch": "^1.6.1",
|
||||
"@vue/eslint-config-typescript": "^12.0.0",
|
||||
"d3": "^7.8.5",
|
||||
"vue": "^3.3.4",
|
||||
"vue-cookies": "^1.8.3",
|
||||
"vue-router": "^4.2.5"
|
||||
},
|
||||
"devDependencies": {
|
||||
"@types/d3": "^7.4.3",
|
||||
"@vitejs/plugin-vue": "^4.2.3",
|
||||
"@vue/eslint-config-prettier": "^8.0.0",
|
||||
"eslint": "^8.56.0",
|
||||
"eslint-config-prettier": "^9.1.0",
|
||||
"eslint-plugin-import": "^2.29.1",
|
||||
"eslint-plugin-json": "^3.1.0",
|
||||
"eslint-plugin-prettier": "^5.0.1",
|
||||
"eslint-plugin-vue": "^9.19.2",
|
||||
"typescript": "^5.0.2",
|
||||
"vite": "^4.4.5",
|
||||
"vite-plugin-eslint": "^1.8.1",
|
||||
"vue-tsc": "^1.8.16"
|
||||
}
|
||||
}
|
||||
|
||||
@ -1,10 +0,0 @@
|
||||
module.exports = {
|
||||
env: {
|
||||
node: true,
|
||||
},
|
||||
extends: ["eslint:recommended", "plugin:vue/vue3-recommended", "prettier"],
|
||||
rules: {
|
||||
// override/add rules settings here, such as:
|
||||
// 'vue/no-unused-vars': 'error'
|
||||
},
|
||||
};
|
||||
@ -4,7 +4,7 @@
|
||||
<div id="router">
|
||||
<!-- route outlet -->
|
||||
<!-- component matched by the route will render here -->
|
||||
<router-view></router-view>
|
||||
<router-view />
|
||||
</div>
|
||||
</template>
|
||||
|
||||
|
||||
7
src/app.config.ts
Normal file
7
src/app.config.ts
Normal file
@ -0,0 +1,7 @@
|
||||
export const apiBaseUrl = import.meta.env.VITE_API_BASE_URL;
|
||||
export const routerBase = import.meta.env.VITE_ROUTER_BASE;
|
||||
|
||||
export default {
|
||||
apiBaseUrl,
|
||||
routerBase,
|
||||
};
|
||||
79
src/components/CallRiskScoreBar.vue
Normal file
79
src/components/CallRiskScoreBar.vue
Normal file
@ -0,0 +1,79 @@
|
||||
<script lang="ts" setup>
|
||||
import * as d3 from "d3";
|
||||
import { onMounted } from "vue";
|
||||
|
||||
const props = defineProps({
|
||||
score: { type: Number, default: 30 },
|
||||
});
|
||||
|
||||
const id = "csrScoreBar";
|
||||
const width = 300;
|
||||
|
||||
onMounted(() => {
|
||||
drawScale(id, d3.interpolateRdYlGn);
|
||||
});
|
||||
|
||||
function drawScale(id: string, interpolator: number) {
|
||||
var data = Array.from(Array(100).keys());
|
||||
|
||||
var cScale = d3.scaleSequential().interpolator(interpolator).domain([0, 99]);
|
||||
|
||||
var xScale = d3.scaleLinear().domain([0, 99]).range([0, width]);
|
||||
|
||||
d3.select("#" + id)
|
||||
.selectAll("rect")
|
||||
.data(data)
|
||||
.enter()
|
||||
.append("rect")
|
||||
.attr("x", (d) => Math.floor(xScale(d)))
|
||||
.attr("y", 0)
|
||||
.attr("height", 40)
|
||||
.attr("width", (d) => {
|
||||
if (d == 99) {
|
||||
return 6;
|
||||
}
|
||||
return Math.floor(xScale(d + 1)) - Math.floor(xScale(d)) + 1;
|
||||
})
|
||||
.attr("fill", (d) => {
|
||||
if (d >= props.score && d < props.score + 1) {
|
||||
return "black";
|
||||
}
|
||||
return cScale(d);
|
||||
});
|
||||
}
|
||||
</script>
|
||||
<template>
|
||||
<div class="crsContainer">
|
||||
<div></div>
|
||||
<font-awesome-icon
|
||||
id="auth"
|
||||
:icon="['fas', 'user-shield']"
|
||||
size="2xl"
|
||||
style="color: #45b408"
|
||||
/>
|
||||
Call Risk Score is {{ score }}
|
||||
<div class="img-overlay-wrap">
|
||||
<svg :id="id" :width="width" height="40"></svg>
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style>
|
||||
.crsContainer {
|
||||
align-items: flex-start;
|
||||
border: 2px solid #45b408;
|
||||
border-radius: 5px;
|
||||
font-family: OpenSans, Ariel, sans-serif;
|
||||
font-size: 11px;
|
||||
gap: 8px;
|
||||
margin: 8px;
|
||||
padding: 11px 16px 11px 12px;
|
||||
}
|
||||
|
||||
.img-overlay-wrap svg {
|
||||
/* <= optional, for responsiveness */
|
||||
display: block;
|
||||
max-width: 100%;
|
||||
height: auto;
|
||||
margin: 8px;
|
||||
}
|
||||
</style>
|
||||
52
src/components/DaVinciAuthentication.vue
Normal file
52
src/components/DaVinciAuthentication.vue
Normal file
@ -0,0 +1,52 @@
|
||||
<script lang="ts" setup>
|
||||
defineProps({
|
||||
authenticated: { type: Boolean, default: false },
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<div class="transferSummary">
|
||||
<div v-if="authenticated" class="authboxgreen">
|
||||
<font-awesome-icon
|
||||
id="auth"
|
||||
:icon="['fas', 'user-shield']"
|
||||
size="2xl"
|
||||
style="color: #45b408"
|
||||
/>
|
||||
Customer Authenticated
|
||||
</div>
|
||||
<div v-else class="authboxred">
|
||||
<font-awesome-icon id="noauth" :icon="['fas', 'user-lock']" size="2xl" />
|
||||
Customer Not Authenticated
|
||||
</div>
|
||||
</div>
|
||||
</template>
|
||||
<style>
|
||||
.authboxgreen,
|
||||
.authboxred {
|
||||
margin: 8px;
|
||||
border-radius: 5px;
|
||||
padding: 11px 16px 11px 12px;
|
||||
align-items: flex-start;
|
||||
gap: 8px;
|
||||
border-radius: 5px;
|
||||
font-size: 14px;
|
||||
font-family: OpenSans, Ariel, sans-serif;
|
||||
font-size: 11px;
|
||||
}
|
||||
|
||||
.authboxgreen {
|
||||
border: 2px solid #45b408;
|
||||
}
|
||||
|
||||
.authboxred {
|
||||
border: 2px solid #e03800;
|
||||
}
|
||||
|
||||
#auth {
|
||||
color: #45b408;
|
||||
}
|
||||
|
||||
#noauth {
|
||||
color: #e03800;
|
||||
}
|
||||
</style>
|
||||
12
src/components/ErrorMessage.vue
Normal file
12
src/components/ErrorMessage.vue
Normal file
@ -0,0 +1,12 @@
|
||||
<script lang="ts" setup>
|
||||
defineProps({
|
||||
message: { type: String, default: "No message property set" },
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<p v-if="message">
|
||||
{{ message }}
|
||||
</p>
|
||||
</template>
|
||||
|
||||
<style></style>
|
||||
35
src/components/IntegrationCard.vue
Normal file
35
src/components/IntegrationCard.vue
Normal file
@ -0,0 +1,35 @@
|
||||
<script lang="ts" setup>
|
||||
defineProps({
|
||||
title: { type: String, default: "Integration Card" },
|
||||
doc: {
|
||||
type: String,
|
||||
default: "<html><body><p>HTML document</p></body></html>",
|
||||
},
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<h3>{{ title }}</h3>
|
||||
<iframe
|
||||
class="integrationCard"
|
||||
:srcdoc="doc"
|
||||
scrolling="no"
|
||||
onload="resizeIframe(this)"
|
||||
/>
|
||||
</template>
|
||||
<style>
|
||||
span.customer {
|
||||
color: #ff0000;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
span.iva {
|
||||
color: #0000a0;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
iframe.integrationCard {
|
||||
border: 0;
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
}
|
||||
</style>
|
||||
108
src/components/TransferSummary.vue
Normal file
108
src/components/TransferSummary.vue
Normal file
@ -0,0 +1,108 @@
|
||||
<script lang="ts" setup>
|
||||
defineProps({
|
||||
summary: { type: String, default: "Summary not available" },
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<div class="transferSummaryContainer">
|
||||
<table>
|
||||
<tr>
|
||||
<td>
|
||||
<svg
|
||||
id=" Layer_1"
|
||||
version="1.1"
|
||||
xmlns="http://www.w3.org/2000/svg"
|
||||
xmlns:xlink="http://www.w3.org/1999/xlink"
|
||||
x="0px"
|
||||
y="0px"
|
||||
viewBox="0 0 98 89"
|
||||
xml:space="preserve"
|
||||
width="22"
|
||||
height="22"
|
||||
fill="none"
|
||||
>
|
||||
<g>
|
||||
<path
|
||||
class="st0"
|
||||
d="M78.8,85H19.3c-3.1,0-5.7-2.5-5.7-5.7V33.7c0-3.1,2.5-5.7,5.7-5.7h59.5c3.1,0,5.7,2.5,5.7,5.7v45.6
|
||||
C84.5,82.5,81.9,85,78.8,85z"
|
||||
/>
|
||||
<g>
|
||||
<circle class="st1" cx="35.7" cy="51.9" r="6.7" />
|
||||
<circle class="st1" cx="62.1" cy="51.9" r="6.7" />
|
||||
</g>
|
||||
<circle class="st0" cx="49" cy="9.1" r="5.1" />
|
||||
<line class="st0" x1="49" y1="28" x2="49" y2="14.1" />
|
||||
<path
|
||||
class="st2"
|
||||
d="M37.9,74.8c0,0,3.8,0,11.1,0s11.1-2.5,11.1-2.5"
|
||||
/>
|
||||
<path
|
||||
class="st0"
|
||||
d="M70.5,64.4h-43c-3.4,0-6.2-2.8-6.2-6.2V45.6c0-3.4,2.8-6.2,6.2-6.2h43c3.4,0,6.2,2.8,6.2,6.2v12.7
|
||||
C76.7,61.7,73.9,64.4,70.5,64.4z"
|
||||
/>
|
||||
<path
|
||||
class="st0"
|
||||
d="M13.6,64.4h-2.7c-3.4,0-6.2-2.8-6.2-6.2V45.6c0-3.4,2.8-6.2,6.2-6.2h2.7"
|
||||
/>
|
||||
<path
|
||||
class="st0"
|
||||
d="M84.5,39.4h2.7c3.4,0,6.2,2.8,6.2,6.2v12.7c0,3.4-2.8,6.2-6.2,6.2h-2.7"
|
||||
/>
|
||||
</g>
|
||||
</svg>
|
||||
</td>
|
||||
<td style="font-weight: bold">Transfer Bot</td>
|
||||
</tr>
|
||||
<tr>
|
||||
<td />
|
||||
<td>{{ summary }}</td>
|
||||
</tr>
|
||||
</table>
|
||||
</div>
|
||||
</template>
|
||||
<style>
|
||||
.transferSummaryContainer {
|
||||
align-items: flex-start;
|
||||
border: 2px solid #45b408;
|
||||
border-radius: 5px;
|
||||
color: white;
|
||||
font-family: OpenSans, Ariel, sans-serif;
|
||||
font-size: 11px;
|
||||
gap: 8px;
|
||||
margin: 8px;
|
||||
padding: 11px 16px 11px 12px;
|
||||
background: var(--button-emphasized-regular, #0c874b);
|
||||
}
|
||||
|
||||
.st0 {
|
||||
fill: none;
|
||||
stroke: white;
|
||||
stroke-width: 3;
|
||||
stroke-linejoin: round;
|
||||
stroke-miterlimit: 10;
|
||||
}
|
||||
|
||||
.st1 {
|
||||
fill: none;
|
||||
stroke: white;
|
||||
stroke-width: 2.6179;
|
||||
stroke-linejoin: round;
|
||||
stroke-miterlimit: 10;
|
||||
}
|
||||
|
||||
.st2 {
|
||||
fill: none;
|
||||
stroke: white;
|
||||
stroke-width: 3;
|
||||
stroke-linecap: round;
|
||||
stroke-linejoin: round;
|
||||
stroke-miterlimit: 10;
|
||||
}
|
||||
|
||||
svg {
|
||||
margin: 8px;
|
||||
enable-background: new 0 0 98 89;
|
||||
}
|
||||
</style>
|
||||
@ -1,6 +1,13 @@
|
||||
<script lang="ts" setup>
|
||||
// eslint-disable-next-line
|
||||
const props = defineProps(["label", "value"]);
|
||||
const props = defineProps({
|
||||
label: { type: String, default: "" },
|
||||
value: { type: String, default: "" },
|
||||
});
|
||||
const value = props.value;
|
||||
if (!props.value) {
|
||||
console.error("No label property");
|
||||
}
|
||||
const rows = Math.ceil(props.value.length / 18);
|
||||
</script>
|
||||
<template>
|
||||
|
||||
54
src/helpers/index.ts
Normal file
54
src/helpers/index.ts
Normal file
@ -0,0 +1,54 @@
|
||||
import { apiBaseUrl } from "../app.config.js";
|
||||
import type { SessionIdentifier } from "../types/index";
|
||||
|
||||
export function getAuthKeyFromProperties(props: SessionIdentifier) {
|
||||
let authKey;
|
||||
|
||||
if (props.sessionIdentifier && props.sessionIdentifier.length > 0) {
|
||||
authKey = props.sessionIdentifier;
|
||||
} else {
|
||||
throw new Error(
|
||||
"_sessionIdentifier property not found (check query params)",
|
||||
);
|
||||
}
|
||||
return authKey;
|
||||
}
|
||||
|
||||
export function getTenantProperty(key: string, props: SessionIdentifier) {
|
||||
return new Promise((resolve, reject) => {
|
||||
if (!props) {
|
||||
reject("no props provided for authentication");
|
||||
return;
|
||||
}
|
||||
if (!key || key.length == 0) {
|
||||
reject("no key provided");
|
||||
return;
|
||||
}
|
||||
|
||||
const authKey = getAuthKeyFromProperties(props);
|
||||
console.log(`Fetching TPS Property [${key}]`);
|
||||
fetch(`${apiBaseUrl}/tps/${key}?authKey=${authKey}`, {
|
||||
credentials: "include", // fetch won't send cookies unless you set credentials
|
||||
})
|
||||
.then((response) => {
|
||||
// check for error response
|
||||
if (!response.ok) {
|
||||
reject(response.body || response.statusText);
|
||||
}
|
||||
response
|
||||
.json()
|
||||
.then((data: { data: { value: string } }) => {
|
||||
console.log("Found Property:" + JSON.stringify(data));
|
||||
resolve(data.data.value);
|
||||
})
|
||||
.catch((error) => {
|
||||
console.error(error);
|
||||
reject(error);
|
||||
});
|
||||
})
|
||||
.catch((error) => {
|
||||
console.error(error);
|
||||
reject(error);
|
||||
});
|
||||
});
|
||||
}
|
||||
23
src/main.ts
23
src/main.ts
@ -1,6 +1,25 @@
|
||||
import { createApp } from "vue";
|
||||
import { Component, createApp } from "vue";
|
||||
import "./style.css";
|
||||
import App from "./App.vue";
|
||||
import router from "./router";
|
||||
|
||||
createApp(App).use(router).mount("#app");
|
||||
import VueCookies from "vue-cookies";
|
||||
|
||||
/* import the fontawesome core */
|
||||
import { library } from "@fortawesome/fontawesome-svg-core";
|
||||
|
||||
/* import font awesome icon component */
|
||||
import { FontAwesomeIcon } from "@fortawesome/vue-fontawesome";
|
||||
|
||||
/* import specific icons */
|
||||
import { faUserShield, faUserLock } from "@fortawesome/free-solid-svg-icons";
|
||||
|
||||
/* add icons to the library */
|
||||
library.add(faUserShield);
|
||||
library.add(faUserLock);
|
||||
|
||||
createApp(App as Component)
|
||||
.use(router)
|
||||
.use(VueCookies, { expires: "7d" })
|
||||
.component("font-awesome-icon", FontAwesomeIcon)
|
||||
.mount("#app");
|
||||
|
||||
@ -1,17 +1,22 @@
|
||||
import { createRouter, createWebHashHistory } from "vue-router";
|
||||
import Home from "../views/Home.vue";
|
||||
import Home from "../views/HomePage.vue";
|
||||
import TelephonyContext from "../views/TelephonyContext.vue";
|
||||
import { Component } from "vue";
|
||||
|
||||
const routes = [
|
||||
{ path: "/", component: Home },
|
||||
{ path: "/", component: Home as Component },
|
||||
{
|
||||
path: "/telephonyContext/",
|
||||
name: "telephonyContext",
|
||||
components: { default: TelephonyContext },
|
||||
components: { default: TelephonyContext as Component },
|
||||
props: {
|
||||
default: (route: { params: any; query: any }) => ({
|
||||
default: (route: {
|
||||
params: object;
|
||||
query: { _sessionIdentifier: string };
|
||||
}) => ({
|
||||
...route.params,
|
||||
...route.query,
|
||||
sessionIdentifier: route.query._sessionIdentifier,
|
||||
}),
|
||||
},
|
||||
},
|
||||
|
||||
3
src/types/index.ts
Normal file
3
src/types/index.ts
Normal file
@ -0,0 +1,3 @@
|
||||
export interface SessionIdentifier {
|
||||
sessionIdentifier: string;
|
||||
}
|
||||
19
src/views/DaVinciView.vue
Normal file
19
src/views/DaVinciView.vue
Normal file
@ -0,0 +1,19 @@
|
||||
<script lang="ts" setup>
|
||||
import TransferSummary from "../components/TransferSummary.vue";
|
||||
import DaVinciAuthentication from "../components/DaVinciAuthentication.vue";
|
||||
import CallRiskScoreBar from "../components/CallRiskScoreBar.vue";
|
||||
|
||||
defineProps({
|
||||
summary: { type: String, default: "<h4>Summary not available.</h4>" },
|
||||
authenticated: { type: Boolean, default: false },
|
||||
crsScore: { type: Number, default: 63 },
|
||||
});
|
||||
</script>
|
||||
<template>
|
||||
<div class="davinci">
|
||||
<h3>Da Vinci AI</h3>
|
||||
<DaVinciAuthentication :authenticated="authenticated" />
|
||||
<CallRiskScoreBar :score="crsScore" />
|
||||
<TransferSummary :summary="summary" />
|
||||
</div>
|
||||
</template>
|
||||
@ -4,9 +4,10 @@
|
||||
<ul>
|
||||
<li>
|
||||
<router-link
|
||||
to="/telephonyContext?ani=+13125138223&dnis=unknown&queue=GeneralInquires&direction=INBOUND&channel=AmazonConnect&type=Voice&_sessionIdentifier=bc93f1fc"
|
||||
>Telephony Context</router-link
|
||||
to="/telephonyContext?ani=+13125138223&dnis=unknown&queue=GeneralInquires&direction=INBOUND&channel=AmazonConnect&type=Voice&transferSummary=summary&integrationCardTitle=title&integrationCardDoc=doc&_sessionIdentifier=bc93f1fc"
|
||||
>
|
||||
Telephony Context
|
||||
</router-link>
|
||||
</li>
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
@ -1,6 +1,29 @@
|
||||
<script lang="ts" setup>
|
||||
import { ref, onMounted, inject } from "vue";
|
||||
import { getTenantProperty } from "../helpers/index";
|
||||
import VerticalLabelValue from "../components/VerticalLabelValue.vue";
|
||||
defineProps({
|
||||
import ErrorMessage from "../components/ErrorMessage.vue";
|
||||
import IntegrationCard from "../components/IntegrationCard.vue";
|
||||
import DaVinciView from "./DaVinciView.vue";
|
||||
import type { VueCookies } from "vue-cookies";
|
||||
|
||||
import type { SessionIdentifier } from "../types/index";
|
||||
|
||||
var user = {
|
||||
id: 1,
|
||||
name: "Journal",
|
||||
session: "25j_7Sl6xDq2Kc3ym0fmrSSk2xV2XkUkX",
|
||||
};
|
||||
|
||||
const $cookies = inject<VueCookies>("$cookies");
|
||||
if ($cookies) {
|
||||
$cookies.set("user", user);
|
||||
// print user name
|
||||
// eslint-disable-next-line @typescript-eslint/no-unsafe-member-access
|
||||
console.log($cookies.get("user").name);
|
||||
}
|
||||
|
||||
const props = defineProps({
|
||||
channel: { type: String, default: "" },
|
||||
type: { type: String, default: "" },
|
||||
queue: { type: String, default: "" },
|
||||
@ -8,85 +31,112 @@ defineProps({
|
||||
ani: { type: String, default: "" },
|
||||
dnis: { type: String, default: "" },
|
||||
startTime: { type: String, default: "" },
|
||||
transferSummary: { type: String, default: "" },
|
||||
username: { type: String, default: "" },
|
||||
sessionIdentifier: { type: String, default: "" },
|
||||
transferSummary: { type: String, default: "", required: true },
|
||||
integrationCardTitle: { type: String, default: "", required: true },
|
||||
integrationCardDoc: {
|
||||
type: String,
|
||||
default: "",
|
||||
required: true,
|
||||
},
|
||||
authenticated: { type: String, default: "false" },
|
||||
crsScore: { type: String, default: "0" },
|
||||
});
|
||||
|
||||
const errorMessage = ref("");
|
||||
const transferSummaryValue = ref("");
|
||||
const integrationCardTitleValue = ref("");
|
||||
const integrationCardDocValue = ref(props.integrationCardDoc);
|
||||
|
||||
onMounted(() => {
|
||||
fetchData();
|
||||
});
|
||||
|
||||
function setValueFromTPS(
|
||||
reference: { value: string },
|
||||
param: string,
|
||||
props: SessionIdentifier,
|
||||
) {
|
||||
if (param.startsWith("tps:")) {
|
||||
const tpsProperty = param.substring(4, param.length);
|
||||
getTenantProperty(tpsProperty, props)
|
||||
.then((value: string) => {
|
||||
reference.value = value;
|
||||
})
|
||||
.catch((err: Error) => {
|
||||
errorMessage.value = `${err.message} for TPS property ${tpsProperty}`;
|
||||
});
|
||||
} else {
|
||||
reference.value = param;
|
||||
}
|
||||
}
|
||||
|
||||
function fetchData() {
|
||||
//clear errors
|
||||
errorMessage.value = "";
|
||||
|
||||
setValueFromTPS(transferSummaryValue, props.transferSummary, props);
|
||||
setValueFromTPS(integrationCardTitleValue, props.integrationCardTitle, props);
|
||||
setValueFromTPS(integrationCardDocValue, props.integrationCardDoc, props);
|
||||
}
|
||||
</script>
|
||||
|
||||
<template>
|
||||
<h2>Summary</h2>
|
||||
<div class="customerAccount customer-detail-container" width="100%">
|
||||
<div class="customer-profile-fields vertical-layout">
|
||||
<div
|
||||
class="column-layout"
|
||||
style="width: 100%; max-width: 100%; height: 100%"
|
||||
>
|
||||
<div class="row1 column-layout-row">
|
||||
<div
|
||||
class="blockOuterSpacingRight col1 column-layout-cell"
|
||||
style="width: 25%"
|
||||
>
|
||||
<h3>Telephony Data</h3>
|
||||
<VerticalLabelValue
|
||||
label="Channel"
|
||||
:value="channel"
|
||||
></VerticalLabelValue>
|
||||
<VerticalLabelValue label="Type" :value="type"></VerticalLabelValue>
|
||||
<VerticalLabelValue
|
||||
label="Queue"
|
||||
:value="queue"
|
||||
></VerticalLabelValue>
|
||||
<VerticalLabelValue
|
||||
label="Direction"
|
||||
:value="direction"
|
||||
></VerticalLabelValue>
|
||||
<VerticalLabelValue label="ANI" :value="ani"></VerticalLabelValue>
|
||||
<VerticalLabelValue label="DNIS" :value="dnis"></VerticalLabelValue>
|
||||
</div>
|
||||
<div
|
||||
class="blockOuterSpacingRight col2 column-layout-cell"
|
||||
style="width: 25%"
|
||||
>
|
||||
<h3>Da Vinci Transfer Summary</h3>
|
||||
<ul>
|
||||
<li>
|
||||
<span class="customer">Alice</span> is a new employee who needs
|
||||
access to an application for her work, but she doesn't have the
|
||||
password.
|
||||
</li>
|
||||
<li>
|
||||
She asked the <span class="iva">IVA</span> but they are unable
|
||||
to help her
|
||||
</li>
|
||||
<li>She tries to guess the password, but fails.</li>
|
||||
<li>
|
||||
She uses a hacking tool to find the password, which is
|
||||
"ilovebing".
|
||||
</li>
|
||||
<li>
|
||||
She logs into the application, unaware that the senior developer
|
||||
is monitoring her.
|
||||
</li>
|
||||
</ul>
|
||||
<div>
|
||||
<h2>Summary</h2>
|
||||
|
||||
<div class="customerAccount customer-detail-container" width="100%">
|
||||
<div class="customer-profile-fields vertical-layout">
|
||||
<div
|
||||
class="column-layout"
|
||||
style="width: 100%; max-width: 100%; height: 100%"
|
||||
>
|
||||
<div class="row1 column-layout-row">
|
||||
<div
|
||||
class="blockOuterSpacingRight col1 column-layout-cell"
|
||||
style="width: 25%"
|
||||
>
|
||||
<h3>Telephony Data</h3>
|
||||
<VerticalLabelValue label="Channel" :value="channel" />
|
||||
<VerticalLabelValue label="Type" :value="type" />
|
||||
<VerticalLabelValue label="Queue" :value="queue" />
|
||||
<VerticalLabelValue label="Direction" :value="direction" />
|
||||
<VerticalLabelValue label="ANI" :value="ani" />
|
||||
<VerticalLabelValue label="DNIS" :value="dnis" />
|
||||
</div>
|
||||
<div
|
||||
class="blockOuterSpacingRight col2 column-layout-cell"
|
||||
style="width: 25%"
|
||||
>
|
||||
<DaVinciView
|
||||
:summary="transferSummaryValue"
|
||||
:authenticated="authenticated == 'true'"
|
||||
:crs-score="Number(crsScore)"
|
||||
/>
|
||||
</div>
|
||||
<div
|
||||
class="blockOuterSpacingRight col3 column-layout-cell"
|
||||
style="width: 50%"
|
||||
>
|
||||
<IntegrationCard
|
||||
:title="integrationCardTitleValue"
|
||||
:doc="integrationCardDocValue"
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
` `
|
||||
<ErrorMessage v-if="errorMessage" :message="errorMessage" />
|
||||
</div>
|
||||
</template>
|
||||
<style scoped>
|
||||
@import "https://em28.verint.live/ClientResources/cr/202307201110/-/webclient/themes/default/theme.css";
|
||||
@import "https://em28.verint.live/ClientResources/cr/202307201110/-/webclient/css/extensions/corecommon.css";
|
||||
@import "https://shared-eo.verint.live/ClientResources/cr/202307201110/-/webclient/themes/default/theme.css";
|
||||
@import "https://shared-eo.verint.live/ClientResources/cr/202307201110/-/webclient/css/extensions/corecommon.css";
|
||||
|
||||
p {
|
||||
size: 24pt;
|
||||
}
|
||||
|
||||
span.customer {
|
||||
color: #ff0000;
|
||||
font-weight: bold;
|
||||
}
|
||||
|
||||
span.iva {
|
||||
color: #0000a0;
|
||||
font-weight: bold;
|
||||
}
|
||||
</style>
|
||||
../types/index
|
||||
|
||||
10
src/vite-env.d.ts
vendored
10
src/vite-env.d.ts
vendored
@ -1 +1,11 @@
|
||||
/// <reference types="vite/client" />
|
||||
|
||||
interface ImportMetaEnv {
|
||||
readonly VITE_API_BASE_URL: string;
|
||||
readonly VITE_ROUTER_BASE: string;
|
||||
// more env variables...
|
||||
}
|
||||
|
||||
interface ImportMeta {
|
||||
readonly env: ImportMetaEnv;
|
||||
}
|
||||
|
||||
7
tsconfig.eslint.json
Normal file
7
tsconfig.eslint.json
Normal file
@ -0,0 +1,7 @@
|
||||
{
|
||||
"extends": "./tsconfig.json",
|
||||
"include": [
|
||||
// ...
|
||||
"babel.config.js"
|
||||
]
|
||||
}
|
||||
@ -1,4 +1,5 @@
|
||||
import { defineConfig } from "vite";
|
||||
import eslintPlugin from "vite-plugin-eslint";
|
||||
import vue from "@vitejs/plugin-vue";
|
||||
|
||||
// https://vitejs.dev/config/
|
||||
@ -6,6 +7,6 @@ export default defineConfig(({ command }) => {
|
||||
if (command === "build") {
|
||||
return { plugins: [vue()], base: "/ca_vue_apps/dist" };
|
||||
} else {
|
||||
return { plugins: [vue()] };
|
||||
return { plugins: [eslintPlugin(), vue()] };
|
||||
}
|
||||
});
|
||||
|
||||
Loading…
x
Reference in New Issue
Block a user